This commit is contained in:
purplerain 2023-05-18 12:23:26 +00:00
parent 9e7f51724c
commit 4b78db449c
Signed by: purplerain
GPG key ID: F42C07F07E2E35B7
42 changed files with 1110 additions and 143 deletions

View file

@ -45,6 +45,7 @@ ENTRY_NB(bcopy)
/* fall into memmove */ /* fall into memmove */
NENTRY(memmove) NENTRY(memmove)
endbr64
RETGUARD_SETUP(memmove, r10) RETGUARD_SETUP(memmove, r10)
movq %rdi,%r11 /* save dest */ movq %rdi,%r11 /* save dest */
movq %rdx,%rcx movq %rdx,%rcx

View file

@ -1,4 +1,4 @@
/* $OpenBSD: Ovfork.S,v 1.9 2023/01/11 01:55:17 mortimer Exp $ */ /* $OpenBSD: Ovfork.S,v 1.10 2023/05/18 04:26:06 guenther Exp $ */
/* $NetBSD: Ovfork.S,v 1.2 2002/06/03 18:30:33 fvdl Exp $ */ /* $NetBSD: Ovfork.S,v 1.2 2002/06/03 18:30:33 fvdl Exp $ */
/*- /*-
@ -39,17 +39,24 @@
#include "SYS.h" #include "SYS.h"
/*
* This is written to support a potential vfork(2) that would share
* the parent's vmspace to the child. For that, the parent must
* not rely on anything on the stack at the time of the syscall,
* as the child will overwrite it. So, keep both the return address
* and retguard value in registers (r9 and r8) across the call.
* This used to do an indirect jump on success, but that doesn't
* work if indirect-branch-tracking is enabled as the _caller_ of
* this vfork() stub won't know to place an endbr64 instruction
* after the call. So, just push it back on the stack and return.
*/
SYSENTRY_HIDDEN(vfork) SYSENTRY_HIDDEN(vfork)
RETGUARD_SETUP(_thread_sys_vfork, r8);
popq %r9 /* my rta into r9 */ popq %r9 /* my rta into r9 */
RETGUARD_SETUP(_thread_sys_vfork, r11);
RETGUARD_PUSH(r11);
SYSTRAP(vfork) SYSTRAP(vfork)
RETGUARD_POP(r11)
jc 1f
jmp *%r9
1:
pushq %r9 pushq %r9
jnc 1f
SET_ERRNO SET_ERRNO
RETGUARD_CHECK(_thread_sys_vfork, r11); 1: RETGUARD_CHECK(_thread_sys_vfork, r8);
ret ret
SYSCALL_END_HIDDEN(vfork) SYSCALL_END_HIDDEN(vfork)

View file

@ -1,4 +1,4 @@
/* $OpenBSD: getwd.c,v 1.13 2021/12/16 19:12:43 millert Exp $ */ /* $OpenBSD: getwd.c,v 1.14 2023/05/18 16:11:09 guenther Exp $ */
/*- /*-
* Copyright (c) 1990 The Regents of the University of California. * Copyright (c) 1990 The Regents of the University of California.
* All rights reserved. * All rights reserved.
@ -34,9 +34,6 @@
#include <string.h> #include <string.h>
#include <unistd.h> #include <unistd.h>
int __getcwd(char *buf, size_t len);
PROTO_NORMAL(__getcwd);
char * char *
getwd(char *buf) getwd(char *buf)
{ {

View file

@ -1,4 +1,4 @@
/* $OpenBSD: getcwd.c,v 1.21 2016/05/07 19:48:00 guenther Exp $ */ /* $OpenBSD: getcwd.c,v 1.22 2023/05/18 16:11:09 guenther Exp $ */
/* /*
* Copyright (c) 2005 Marius Eriksen <marius@openbsd.org> * Copyright (c) 2005 Marius Eriksen <marius@openbsd.org>
@ -21,9 +21,6 @@
#include <stdlib.h> #include <stdlib.h>
#include <unistd.h> #include <unistd.h>
int __getcwd(char *buf, size_t len);
PROTO_NORMAL(__getcwd);
char * char *
getcwd(char *buf, size_t size) getcwd(char *buf, size_t size)
{ {

View file

@ -1,4 +1,4 @@
/* $OpenBSD: stdlib.h,v 1.16 2019/05/10 15:03:24 otto Exp $ */ /* $OpenBSD: stdlib.h,v 1.17 2023/05/18 16:11:09 guenther Exp $ */
/* $NetBSD: stdlib.h,v 1.25 1995/12/27 21:19:08 jtc Exp $ */ /* $NetBSD: stdlib.h,v 1.25 1995/12/27 21:19:08 jtc Exp $ */
/*- /*-
@ -45,11 +45,14 @@ __END_HIDDEN_DECLS
extern char **environ; extern char **environ;
extern char *__progname; extern char *__progname;
int __realpath(const char *pathname, char *resolved);
#if 0 #if 0
/*extern PROTO_NORMAL(suboptarg);*/ /*extern PROTO_NORMAL(suboptarg);*/
#endif #endif
PROTO_NORMAL(__mb_cur_max); PROTO_NORMAL(__mb_cur_max);
PROTO_NORMAL(__realpath);
PROTO_STD_DEPRECATED(_Exit); PROTO_STD_DEPRECATED(_Exit);
PROTO_DEPRECATED(a64l); PROTO_DEPRECATED(a64l);
PROTO_NORMAL(abort); PROTO_NORMAL(abort);

View file

@ -0,0 +1,26 @@
/* $OpenBSD: event.h,v 1.1 2023/05/18 16:11:09 guenther Exp $ */
/*
* Copyright (c) 2023 Philip Guenther <guenther@openbsd.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#ifndef _LIBC_SYS_EVENT_H_
#define _LIBC_SYS_EVENT_H_
#include_next <sys/event.h>
PROTO_NORMAL(kevent);
PROTO_NORMAL(kqueue);
#endif /* !_LIBC_SYS_EVENT_H_ */

View file

@ -0,0 +1,26 @@
/* $OpenBSD: ktrace.h,v 1.1 2023/05/18 16:07:12 guenther Exp $ */
/*
* Copyright (c) 2023 Philip Guenther <guenther@openbsd.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#ifndef _LIBC_SYS_KTRACE_H_
#define _LIBC_SYS_KTRACE_H_
#include_next <sys/ktrace.h>
PROTO_NORMAL(ktrace);
PROTO_NORMAL(utrace);
#endif /* !_LIBC_SYS_KTRACE_H_ */

28
lib/libc/hidden/sys/shm.h Normal file
View file

@ -0,0 +1,28 @@
/* $OpenBSD: shm.h,v 1.1 2023/05/18 16:11:09 guenther Exp $ */
/*
* Copyright (c) 2023 Philip Guenther <guenther@openbsd.org>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#ifndef _LIBC_SYS_SHM_H_
#define _LIBC_SYS_SHM_H_
#include_next <sys/shm.h>
PROTO_NORMAL(shmat);
PROTO_NORMAL(shmctl);
PROTO_NORMAL(shmdt);
PROTO_NORMAL(shmget);
#endif /* !_LIBC_SYS_SHM_H_ */

View file

@ -1,4 +1,4 @@
/* $OpenBSD: stat.h,v 1.2 2015/09/14 10:11:54 guenther Exp $ */ /* $OpenBSD: stat.h,v 1.3 2023/05/18 16:11:09 guenther Exp $ */
/* /*
* Copyright (c) 2015 Philip Guenther <guenther@openbsd.org> * Copyright (c) 2015 Philip Guenther <guenther@openbsd.org>
* *
@ -21,6 +21,7 @@
#include_next <sys/stat.h> #include_next <sys/stat.h>
PROTO_NORMAL(chflags); PROTO_NORMAL(chflags);
PROTO_NORMAL(chflagsat);
PROTO_NORMAL(chmod); PROTO_NORMAL(chmod);
PROTO_NORMAL(fchflags); PROTO_NORMAL(fchflags);
PROTO_NORMAL(fchmod); PROTO_NORMAL(fchmod);

View file

@ -1,4 +1,4 @@
/* $OpenBSD: unistd.h,v 1.11 2018/07/13 09:25:22 beck Exp $ */ /* $OpenBSD: unistd.h,v 1.12 2023/05/18 16:11:09 guenther Exp $ */
/* /*
* Copyright (c) 2015 Philip Guenther <guenther@openbsd.org> * Copyright (c) 2015 Philip Guenther <guenther@openbsd.org>
* *
@ -25,6 +25,10 @@ __BEGIN_HIDDEN_DECLS
extern int _pagesize; extern int _pagesize;
__END_HIDDEN_DECLS __END_HIDDEN_DECLS
/* the real syscall behind getcwd(3) and getwd(3) */
int __getcwd(char *buf, size_t len);
PROTO_NORMAL(__getcwd);
PROTO_NORMAL(__tfork_thread); PROTO_NORMAL(__tfork_thread);
PROTO_NORMAL(_exit); PROTO_NORMAL(_exit);
PROTO_NORMAL(access); PROTO_NORMAL(access);
@ -87,6 +91,7 @@ PROTO_NORMAL(getresgid);
PROTO_NORMAL(getresuid); PROTO_NORMAL(getresuid);
PROTO_NORMAL(getsid); PROTO_NORMAL(getsid);
PROTO_NORMAL(getthrid); PROTO_NORMAL(getthrid);
PROTO_NORMAL(getthrname);
PROTO_NORMAL(getuid); PROTO_NORMAL(getuid);
PROTO_DEPRECATED(getusershell); PROTO_DEPRECATED(getusershell);
PROTO_DEPRECATED(getwd); PROTO_DEPRECATED(getwd);
@ -142,6 +147,7 @@ PROTO_NORMAL(setresgid);
PROTO_NORMAL(setresuid); PROTO_NORMAL(setresuid);
PROTO_NORMAL(setreuid); PROTO_NORMAL(setreuid);
PROTO_NORMAL(setsid); PROTO_NORMAL(setsid);
PROTO_NORMAL(setthrname);
PROTO_NORMAL(setuid); PROTO_NORMAL(setuid);
PROTO_DEPRECATED(setusershell); PROTO_DEPRECATED(setusershell);
/*PROTO_CANCEL(sleep);*/ /*PROTO_CANCEL(sleep);*/

View file

@ -1,4 +1,4 @@
/* $OpenBSD: realpath.c,v 1.27 2019/07/05 05:04:26 deraadt Exp $ */ /* $OpenBSD: realpath.c,v 1.28 2023/05/18 16:11:10 guenther Exp $ */
/* /*
* Copyright (c) 2019 Bob Beck <beck@openbsd.org> * Copyright (c) 2019 Bob Beck <beck@openbsd.org>
* Copyright (c) 2019 Theo de Raadt <deraadt@openbsd.org> * Copyright (c) 2019 Theo de Raadt <deraadt@openbsd.org>
@ -24,9 +24,6 @@
#include <syslog.h> #include <syslog.h>
#include <stdarg.h> #include <stdarg.h>
int __realpath(const char *pathname, char *resolved);
PROTO_NORMAL(__realpath);
/* /*
* wrapper for kernel __realpath * wrapper for kernel __realpath
*/ */

View file

@ -1,4 +1,4 @@
/* $OpenBSD: ldasm.S,v 1.30 2019/05/10 13:29:21 guenther Exp $ */ /* $OpenBSD: ldasm.S,v 1.31 2023/05/18 16:33:39 guenther Exp $ */
/* /*
* Copyright (c) 2002,2004 Dale Rahn * Copyright (c) 2002,2004 Dale Rahn
@ -70,6 +70,7 @@ END(_dl_start)
_ENTRY(_dl_bind_start) _ENTRY(_dl_bind_start)
.cfi_startproc .cfi_startproc
.cfi_adjust_cfa_offset 16 .cfi_adjust_cfa_offset 16
endbr64
pushfq # save registers pushfq # save registers
.cfi_adjust_cfa_offset 8 .cfi_adjust_cfa_offset 8
/*.cfi_offset %rflags, -16 */ /*.cfi_offset %rflags, -16 */

View file

@ -1,4 +1,4 @@
/* $OpenBSD: sysctl.c,v 1.258 2021/07/12 15:09:19 beck Exp $ */ /* $OpenBSD: sysctl.c,v 1.259 2023/05/17 22:12:51 kettenis Exp $ */
/* $NetBSD: sysctl.c,v 1.9 1995/09/30 07:12:50 thorpej Exp $ */ /* $NetBSD: sysctl.c,v 1.9 1995/09/30 07:12:50 thorpej Exp $ */
/* /*
@ -132,6 +132,7 @@ struct ctlname ddbname[] = CTL_DDB_NAMES;
struct ctlname audioname[] = CTL_KERN_AUDIO_NAMES; struct ctlname audioname[] = CTL_KERN_AUDIO_NAMES;
struct ctlname videoname[] = CTL_KERN_VIDEO_NAMES; struct ctlname videoname[] = CTL_KERN_VIDEO_NAMES;
struct ctlname witnessname[] = CTL_KERN_WITNESS_NAMES; struct ctlname witnessname[] = CTL_KERN_WITNESS_NAMES;
struct ctlname batteryname[] = CTL_HW_BATTERY_NAMES;
char names[BUFSIZ]; char names[BUFSIZ];
int lastused; int lastused;
@ -223,6 +224,7 @@ int sysctl_chipset(char *, char **, int *, int, int *);
int sysctl_audio(char *, char **, int *, int, int *); int sysctl_audio(char *, char **, int *, int, int *);
int sysctl_video(char *, char **, int *, int, int *); int sysctl_video(char *, char **, int *, int, int *);
int sysctl_witness(char *, char **, int *, int, int *); int sysctl_witness(char *, char **, int *, int, int *);
int sysctl_battery(char *, char **, int *, int, int *);
void vfsinit(void); void vfsinit(void);
char *equ = "="; char *equ = "=";
@ -558,6 +560,11 @@ parse(char *string, int flags)
if (len < 0) if (len < 0)
return; return;
break; break;
case HW_BATTERY:
len = sysctl_battery(string, &bufp, mib, flags, &type);
if (len < 0)
return;
break;
case HW_PHYSMEM: case HW_PHYSMEM:
case HW_USERMEM: case HW_USERMEM:
/* /*
@ -1782,6 +1789,7 @@ struct list tclist = { tcname, KERN_TIMECOUNTER_MAXID };
struct list audiolist = { audioname, KERN_AUDIO_MAXID }; struct list audiolist = { audioname, KERN_AUDIO_MAXID };
struct list videolist = { videoname, KERN_VIDEO_MAXID }; struct list videolist = { videoname, KERN_VIDEO_MAXID };
struct list witnesslist = { witnessname, KERN_WITNESS_MAXID }; struct list witnesslist = { witnessname, KERN_WITNESS_MAXID };
struct list batterylist = { batteryname, HW_BATTERY_MAXID };
/* /*
* handle vfs namei cache statistics * handle vfs namei cache statistics
@ -2911,6 +2919,26 @@ sysctl_witness(char *string, char **bufpp, int mib[], int flags, int *typep)
return (3); return (3);
} }
/*
* Handle battery support
*/
int
sysctl_battery(char *string, char **bufpp, int mib[], int flags,
int *typep)
{
int indx;
if (*bufpp == NULL) {
listall(string, &batterylist);
return (-1);
}
if ((indx = findname(string, "third", bufpp, &batterylist)) == -1)
return (-1);
mib[2] = indx;
*typep = batterylist.list[indx].ctl_type;
return (3);
}
/* /*
* Scan a list of names searching for a particular name. * Scan a list of names searching for a particular name.
*/ */

View file

@ -1,4 +1,4 @@
/* $OpenBSD: cpu.c,v 1.89 2023/04/29 08:50:53 kettenis Exp $ */ /* $OpenBSD: cpu.c,v 1.90 2023/05/17 21:45:41 kettenis Exp $ */
/* /*
* Copyright (c) 2016 Dale Rahn <drahn@dalerahn.com> * Copyright (c) 2016 Dale Rahn <drahn@dalerahn.com>
@ -477,7 +477,16 @@ cpu_identify(struct cpu_info *ci)
printf("\n%s: mismatched ID_AA64ISAR2_EL1", printf("\n%s: mismatched ID_AA64ISAR2_EL1",
ci->ci_dev->dv_xname); ci->ci_dev->dv_xname);
} }
if (READ_SPECIALREG(id_aa64pfr0_el1) != cpu_id_aa64pfr0) { id = READ_SPECIALREG(id_aa64pfr0_el1);
/* Allow CSV2/CVS3 to be different. */
id &= ~ID_AA64PFR0_CSV2_MASK;
id &= ~ID_AA64PFR0_CSV3_MASK;
/* Ignore 32-bit support in all exception levels. */
id &= ~ID_AA64PFR0_EL0_MASK;
id &= ~ID_AA64PFR0_EL1_MASK;
id &= ~ID_AA64PFR0_EL2_MASK;
id &= ~ID_AA64PFR0_EL3_MASK;
if (id != cpu_id_aa64pfr0) {
printf("\n%s: mismatched ID_AA64PFR0_EL1", printf("\n%s: mismatched ID_AA64PFR0_EL1",
ci->ci_dev->dv_xname); ci->ci_dev->dv_xname);
} }
@ -884,6 +893,25 @@ cpu_attach(struct device *parent, struct device *dev, void *aux)
cpu_id_aa64pfr0 = READ_SPECIALREG(id_aa64pfr0_el1); cpu_id_aa64pfr0 = READ_SPECIALREG(id_aa64pfr0_el1);
cpu_id_aa64pfr1 = READ_SPECIALREG(id_aa64pfr1_el1); cpu_id_aa64pfr1 = READ_SPECIALREG(id_aa64pfr1_el1);
/*
* The CSV2/CSV3 "features" are handled on a
* per-processor basis. So it is fine if these fields
* differ between CPU cores. Mask off these fields to
* prevent exporting these to userland.
*/
cpu_id_aa64pfr0 &= ~ID_AA64PFR0_CSV2_MASK;
cpu_id_aa64pfr0 &= ~ID_AA64PFR0_CSV3_MASK;
/*
* We only support 64-bit mode, so we don't care about
* differences in support for 32-bit mode between
* cores. Mask off these fields as well.
*/
cpu_id_aa64pfr0 &= ~ID_AA64PFR0_EL0_MASK;
cpu_id_aa64pfr0 &= ~ID_AA64PFR0_EL1_MASK;
cpu_id_aa64pfr0 &= ~ID_AA64PFR0_EL2_MASK;
cpu_id_aa64pfr0 &= ~ID_AA64PFR0_EL3_MASK;
cpu_identify(ci); cpu_identify(ci);
if (OF_getproplen(ci->ci_node, "clocks") > 0) { if (OF_getproplen(ci->ci_node, "clocks") > 0) {

View file

@ -1,4 +1,4 @@
# $OpenBSD: GENERIC,v 1.267 2023/04/28 05:13:37 phessler Exp $ # $OpenBSD: GENERIC,v 1.269 2023/05/17 23:30:58 patrick Exp $
# #
# GENERIC machine description file # GENERIC machine description file
# #
@ -329,6 +329,8 @@ qcgpio* at fdt? early 1
qciic* at acpi? qciic* at acpi?
qciic* at fdt? qciic* at fdt?
iic* at qciic? iic* at qciic?
qcipcc* at fdt?
qcmtx* at fdt? early 1
qcpdc* at fdt? qcpdc* at fdt?
qcscm* at fdt? qcscm* at fdt?
qcspmi* at fdt? qcspmi* at fdt?

View file

@ -1,4 +1,4 @@
# $OpenBSD: RAMDISK,v 1.200 2023/05/12 21:32:49 uaa Exp $ # $OpenBSD: RAMDISK,v 1.202 2023/05/17 23:30:58 patrick Exp $
machine arm64 machine arm64
maxusers 4 maxusers 4
@ -253,6 +253,8 @@ qcgpio* at fdt? early 1
qciic* at acpi? qciic* at acpi?
qciic* at fdt? qciic* at fdt?
iic* at qciic? iic* at qciic?
qcipcc* at fdt?
qcmtx* at fdt? early 1
qcpdc* at fdt? qcpdc* at fdt?
qcscm* at fdt? qcscm* at fdt?
qcspmi* at fdt? qcspmi* at fdt?

View file

@ -1,4 +1,4 @@
# $OpenBSD: files.fdt,v 1.187 2023/04/28 05:13:37 phessler Exp $ # $OpenBSD: files.fdt,v 1.189 2023/05/17 23:30:58 patrick Exp $
# #
# Config file and device description for machine-independent FDT code. # Config file and device description for machine-independent FDT code.
# Included by ports that need it. # Included by ports that need it.
@ -676,6 +676,16 @@ file dev/fdt/qcgpio_fdt.c qcgpio
attach qciic at fdt with qciic_fdt attach qciic at fdt with qciic_fdt
file dev/fdt/qciic_fdt.c qciic file dev/fdt/qciic_fdt.c qciic
# Qualcomm Inter-Processor Communication controller
device qcipcc
attach qcipcc at fdt
file dev/fdt/qcipcc.c qcipcc
# Qualcomm Hardware Spinlock
device qcmtx
attach qcmtx at fdt
file dev/fdt/qcmtx.c qcmtx
# Qualcomm SCM # Qualcomm SCM
device qcscm device qcscm
attach qcscm at fdt attach qcscm at fdt

269
sys/dev/fdt/qcipcc.c Normal file
View file

@ -0,0 +1,269 @@
/* $OpenBSD: qcipcc.c,v 1.1 2023/05/17 23:19:00 patrick Exp $ */
/*
* Copyright (c) 2023 Patrick Wildt <patrick@blueri.se>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#include <sys/param.h>
#include <sys/systm.h>
#include <sys/device.h>
#include <sys/malloc.h>
#include <machine/bus.h>
#include <machine/fdt.h>
#include <dev/ofw/openfirm.h>
#include <dev/ofw/ofw_misc.h>
#include <dev/ofw/fdt.h>
#define IPCC_SEND_ID 0x0c
#define IPCC_RECV_ID 0x10
#define IPCC_RECV_SIGNAL_ENABLE 0x14
#define IPCC_RECV_SIGNAL_DISABLE 0x18
#define IPCC_RECV_SIGNAL_CLEAR 0x1c
#define IPCC_SIGNAL_ID_SHIFT 0
#define IPCC_SIGNAL_ID_MASK 0xffff
#define IPCC_CLIENT_ID_SHIFT 16
#define IPCC_CLIENT_ID_MASK 0xffff
#define HREAD4(sc, reg) \
(bus_space_read_4((sc)->sc_iot, (sc)->sc_ioh, (reg)))
#define HWRITE4(sc, reg, val) \
bus_space_write_4((sc)->sc_iot, (sc)->sc_ioh, (reg), (val))
struct qcipcc_intrhand {
TAILQ_ENTRY(qcipcc_intrhand) ih_q;
int (*ih_func)(void *);
void *ih_arg;
void *ih_sc;
uint16_t ih_client_id;
uint16_t ih_signal_id;
};
struct qcipcc_softc {
struct device sc_dev;
bus_space_tag_t sc_iot;
bus_space_handle_t sc_ioh;
void *sc_ih;
struct interrupt_controller sc_ic;
TAILQ_HEAD(,qcipcc_intrhand) sc_intrq;
struct mbox_device sc_md;
};
struct qcipcc_channel {
struct qcipcc_softc *ch_sc;
uint32_t ch_client_id;
uint32_t ch_signal_id;
};
int qcipcc_match(struct device *, void *, void *);
void qcipcc_attach(struct device *, struct device *, void *);
const struct cfattach qcipcc_ca = {
sizeof (struct qcipcc_softc), qcipcc_match, qcipcc_attach
};
struct cfdriver qcipcc_cd = {
NULL, "qcipcc", DV_DULL
};
int qcipcc_intr(void *);
void *qcipcc_intr_establish(void *, int *, int, struct cpu_info *,
int (*)(void *), void *, char *);
void qcipcc_intr_disestablish(void *);
void qcipcc_intr_enable(void *);
void qcipcc_intr_disable(void *);
void qcipcc_intr_barrier(void *);
void *qcipcc_channel(void *, uint32_t *, struct mbox_client *);
int qcipcc_send(void *, const void *, size_t);
int
qcipcc_match(struct device *parent, void *match, void *aux)
{
struct fdt_attach_args *faa = aux;
return OF_is_compatible(faa->fa_node, "qcom,ipcc");
}
void
qcipcc_attach(struct device *parent, struct device *self, void *aux)
{
struct qcipcc_softc *sc = (struct qcipcc_softc *)self;
struct fdt_attach_args *faa = aux;
if (faa->fa_nreg < 1) {
printf(": no registers\n");
return;
}
sc->sc_iot = faa->fa_iot;
if (bus_space_map(sc->sc_iot, faa->fa_reg[0].addr,
faa->fa_reg[0].size, 0, &sc->sc_ioh)) {
printf(": can't map registers\n");
return;
}
TAILQ_INIT(&sc->sc_intrq);
sc->sc_ih = fdt_intr_establish(faa->fa_node, IPL_BIO,
qcipcc_intr, sc, sc->sc_dev.dv_xname);
if (sc->sc_ih == NULL) {
printf(": can't establish interrupt\n");
return;
}
printf("\n");
sc->sc_ic.ic_node = faa->fa_node;
sc->sc_ic.ic_cookie = sc;
sc->sc_ic.ic_establish = qcipcc_intr_establish;
sc->sc_ic.ic_disestablish = qcipcc_intr_disestablish;
sc->sc_ic.ic_enable = qcipcc_intr_enable;
sc->sc_ic.ic_disable = qcipcc_intr_disable;
sc->sc_ic.ic_barrier = qcipcc_intr_barrier;
fdt_intr_register(&sc->sc_ic);
sc->sc_md.md_node = faa->fa_node;
sc->sc_md.md_cookie = sc;
sc->sc_md.md_channel = qcipcc_channel;
sc->sc_md.md_send = qcipcc_send;
mbox_register(&sc->sc_md);
}
int
qcipcc_intr(void *arg)
{
struct qcipcc_softc *sc = arg;
struct qcipcc_intrhand *ih;
uint16_t client_id, signal_id;
uint32_t reg;
int handled = 0;
while ((reg = HREAD4(sc, IPCC_RECV_ID)) != ~0) {
client_id = (reg >> IPCC_CLIENT_ID_SHIFT) &
IPCC_CLIENT_ID_MASK;
signal_id = (reg >> IPCC_SIGNAL_ID_SHIFT) &
IPCC_SIGNAL_ID_MASK;
TAILQ_FOREACH(ih, &sc->sc_intrq, ih_q) {
if (ih->ih_client_id != client_id ||
ih->ih_signal_id != signal_id)
continue;
ih->ih_func(ih->ih_arg);
handled = 1;
}
HWRITE4(sc, IPCC_RECV_SIGNAL_CLEAR, reg);
}
return handled;
}
void *
qcipcc_intr_establish(void *cookie, int *cells, int ipl,
struct cpu_info *ci, int (*func)(void *), void *arg, char *name)
{
struct qcipcc_softc *sc = cookie;
struct qcipcc_intrhand *ih;
ih = malloc(sizeof(*ih), M_DEVBUF, M_WAITOK | M_ZERO);
ih->ih_func = func;
ih->ih_arg = arg;
ih->ih_sc = sc;
ih->ih_client_id = cells[0] & IPCC_CLIENT_ID_MASK;
ih->ih_signal_id = cells[1] & IPCC_SIGNAL_ID_MASK;
TAILQ_INSERT_TAIL(&sc->sc_intrq, ih, ih_q);
qcipcc_intr_enable(ih);
if (ipl & IPL_WAKEUP)
intr_set_wakeup(sc->sc_ih);
return ih;
}
void
qcipcc_intr_disestablish(void *cookie)
{
struct qcipcc_intrhand *ih = cookie;
struct qcipcc_softc *sc = ih->ih_sc;
qcipcc_intr_disable(ih);
TAILQ_REMOVE(&sc->sc_intrq, ih, ih_q);
free(ih, M_DEVBUF, sizeof(*ih));
}
void
qcipcc_intr_enable(void *cookie)
{
struct qcipcc_intrhand *ih = cookie;
struct qcipcc_softc *sc = ih->ih_sc;
HWRITE4(sc, IPCC_RECV_SIGNAL_ENABLE,
(ih->ih_client_id << IPCC_CLIENT_ID_SHIFT) |
(ih->ih_signal_id << IPCC_SIGNAL_ID_SHIFT));
}
void
qcipcc_intr_disable(void *cookie)
{
struct qcipcc_intrhand *ih = cookie;
struct qcipcc_softc *sc = ih->ih_sc;
HWRITE4(sc, IPCC_RECV_SIGNAL_DISABLE,
(ih->ih_client_id << IPCC_CLIENT_ID_SHIFT) |
(ih->ih_signal_id << IPCC_SIGNAL_ID_SHIFT));
}
void
qcipcc_intr_barrier(void *cookie)
{
struct qcipcc_intrhand *ih = cookie;
struct qcipcc_softc *sc = ih->ih_sc;
intr_barrier(sc->sc_ih);
}
void *
qcipcc_channel(void *cookie, uint32_t *cells, struct mbox_client *mc)
{
struct qcipcc_softc *sc = cookie;
struct qcipcc_channel *ch;
ch = malloc(sizeof(*ch), M_DEVBUF, M_WAITOK);
ch->ch_sc = sc;
ch->ch_client_id = cells[0] & IPCC_CLIENT_ID_MASK;
ch->ch_signal_id = cells[1] & IPCC_SIGNAL_ID_MASK;
return ch;
}
int
qcipcc_send(void *cookie, const void *data, size_t len)
{
struct qcipcc_channel *ch = cookie;
struct qcipcc_softc *sc = ch->ch_sc;
HWRITE4(sc, IPCC_SEND_ID,
(ch->ch_client_id << IPCC_CLIENT_ID_SHIFT) |
(ch->ch_signal_id << IPCC_SIGNAL_ID_SHIFT));
return 0;
}

117
sys/dev/fdt/qcmtx.c Normal file
View file

@ -0,0 +1,117 @@
/* $OpenBSD: qcmtx.c,v 1.1 2023/05/17 23:30:58 patrick Exp $ */
/*
* Copyright (c) 2023 Patrick Wildt <patrick@blueri.se>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#include <sys/param.h>
#include <sys/systm.h>
#include <sys/device.h>
#include <sys/malloc.h>
#include <machine/bus.h>
#include <machine/fdt.h>
#include <dev/ofw/openfirm.h>
#include <dev/ofw/ofw_misc.h>
#include <dev/ofw/fdt.h>
#define QCMTX_OFF(idx) ((idx) * 0x1000)
#define QCMTX_NUM_LOCKS 32
#define QCMTX_APPS_PROC_ID 1
#define HREAD4(sc, reg) \
(bus_space_read_4((sc)->sc_iot, (sc)->sc_ioh, (reg)))
#define HWRITE4(sc, reg, val) \
bus_space_write_4((sc)->sc_iot, (sc)->sc_ioh, (reg), (val))
struct qcmtx_softc {
struct device sc_dev;
bus_space_tag_t sc_iot;
bus_space_handle_t sc_ioh;
int sc_node;
struct hwlock_device sc_hd;
};
int qcmtx_match(struct device *, void *, void *);
void qcmtx_attach(struct device *, struct device *, void *);
int qcmtx_lock(void *, uint32_t *, int);
const struct cfattach qcmtx_ca = {
sizeof (struct qcmtx_softc), qcmtx_match, qcmtx_attach
};
struct cfdriver qcmtx_cd = {
NULL, "qcmtx", DV_DULL
};
int
qcmtx_match(struct device *parent, void *match, void *aux)
{
struct fdt_attach_args *faa = aux;
return OF_is_compatible(faa->fa_node, "qcom,tcsr-mutex");
}
void
qcmtx_attach(struct device *parent, struct device *self, void *aux)
{
struct qcmtx_softc *sc = (struct qcmtx_softc *)self;
struct fdt_attach_args *faa = aux;
if (faa->fa_nreg < 1) {
printf(": no registers\n");
return;
}
sc->sc_node = faa->fa_node;
sc->sc_iot = faa->fa_iot;
if (bus_space_map(sc->sc_iot, faa->fa_reg[0].addr,
faa->fa_reg[0].size, 0, &sc->sc_ioh)) {
printf(": can't map registers\n");
return;
}
printf("\n");
sc->sc_hd.hd_node = faa->fa_node;
sc->sc_hd.hd_cookie = sc;
sc->sc_hd.hd_lock = qcmtx_lock;
hwlock_register(&sc->sc_hd);
}
int
qcmtx_lock(void *cookie, uint32_t *cells, int lock)
{
struct qcmtx_softc *sc = cookie;
int idx = cells[0];
if (idx >= QCMTX_NUM_LOCKS)
return ENXIO;
if (lock) {
HWRITE4(sc, QCMTX_OFF(idx), QCMTX_APPS_PROC_ID);
if (HREAD4(sc, QCMTX_OFF(idx)) !=
QCMTX_APPS_PROC_ID)
return EAGAIN;
KASSERT(HREAD4(sc, QCMTX_OFF(idx)) == QCMTX_APPS_PROC_ID);
} else {
KASSERT(HREAD4(sc, QCMTX_OFF(idx)) == QCMTX_APPS_PROC_ID);
HWRITE4(sc, QCMTX_OFF(idx), 0);
}
return 0;
}

View file

@ -1,4 +1,4 @@
/* $OpenBSD: qcscm.c,v 1.3 2023/04/28 10:19:07 patrick Exp $ */ /* $OpenBSD: qcscm.c,v 1.4 2023/05/17 23:12:04 patrick Exp $ */
/* /*
* Copyright (c) 2022 Patrick Wildt <patrick@blueri.se> * Copyright (c) 2022 Patrick Wildt <patrick@blueri.se>
* *
@ -43,6 +43,7 @@
#define ARM_SMCCC_STD_CALL (0U << 31) #define ARM_SMCCC_STD_CALL (0U << 31)
#define ARM_SMCCC_FAST_CALL (1U << 31) #define ARM_SMCCC_FAST_CALL (1U << 31)
#define ARM_SMCCC_LP64 (1U << 30) #define ARM_SMCCC_LP64 (1U << 30)
#define ARM_SMCCC_OWNER_SIP 2
#define QCTEE_TZ_OWNER_TZ_APPS 48 #define QCTEE_TZ_OWNER_TZ_APPS 48
#define QCTEE_TZ_OWNER_QSEE_OS 50 #define QCTEE_TZ_OWNER_QSEE_OS 50
@ -68,6 +69,14 @@
#define QCTEE_UEFI_DEVICE_ERROR 0x80000007 #define QCTEE_UEFI_DEVICE_ERROR 0x80000007
#define QCTEE_UEFI_NOT_FOUND 0x8000000e #define QCTEE_UEFI_NOT_FOUND 0x8000000e
#define QCSCM_SVC_PIL 0x02
#define QCSCM_PIL_PAS_INIT_IMAGE 0x01
#define QCSCM_PIL_PAS_MEM_SETUP 0x02
#define QCSCM_PIL_PAS_AUTH_AND_RESET 0x05
#define QCSCM_PIL_PAS_SHUTDOWN 0x06
#define QCSCM_PIL_PAS_IS_SUPPORTED 0x07
#define QCSCM_PIL_PAS_MSS_RESET 0x0a
#define QCSCM_INTERRUPTED 1 #define QCSCM_INTERRUPTED 1
#define QCSCM_ARGINFO_NUM(x) (((x) & 0xf) << 0) #define QCSCM_ARGINFO_NUM(x) (((x) & 0xf) << 0)
@ -730,6 +739,93 @@ qcscm_uefi_rtc_set(uint32_t off)
return 0; return 0;
} }
int
qcscm_pas_init_image(uint32_t peripheral, paddr_t metadata)
{
struct qcscm_softc *sc = qcscm_sc;
uint64_t res[3];
uint64_t args[2];
uint32_t arginfo;
int ret;
if (sc == NULL)
return ENXIO;
arginfo = QCSCM_ARGINFO_NUM(nitems(args));
arginfo |= QCSCM_ARGINFO_TYPE(0, QCSCM_ARGINFO_TYPE_VAL);
arginfo |= QCSCM_ARGINFO_TYPE(1, QCSCM_ARGINFO_TYPE_RW);
args[0] = peripheral;
args[1] = metadata;
/* Make call into TEE */
ret = qcscm_smc_call(sc, ARM_SMCCC_OWNER_SIP, QCSCM_SVC_PIL,
QCSCM_PIL_PAS_INIT_IMAGE, arginfo, args, nitems(args), res);
/* If the call succeeded, check the response status */
if (ret == 0)
ret = res[0];
return ret;
}
int
qcscm_pas_mem_setup(uint32_t peripheral, paddr_t addr, size_t size)
{
struct qcscm_softc *sc = qcscm_sc;
uint64_t res[3];
uint64_t args[3];
uint32_t arginfo;
int ret;
if (sc == NULL)
return ENXIO;
arginfo = QCSCM_ARGINFO_NUM(nitems(args));
arginfo |= QCSCM_ARGINFO_TYPE(0, QCSCM_ARGINFO_TYPE_VAL);
arginfo |= QCSCM_ARGINFO_TYPE(1, QCSCM_ARGINFO_TYPE_VAL);
arginfo |= QCSCM_ARGINFO_TYPE(2, QCSCM_ARGINFO_TYPE_VAL);
args[0] = peripheral;
args[1] = addr;
args[2] = size;
/* Make call into TEE */
ret = qcscm_smc_call(sc, ARM_SMCCC_OWNER_SIP, QCSCM_SVC_PIL,
QCSCM_PIL_PAS_MEM_SETUP, arginfo, args, nitems(args), res);
/* If the call succeeded, check the response status */
if (ret == 0)
ret = res[0];
return ret;
}
int
qcscm_pas_auth_and_reset(uint32_t peripheral)
{
struct qcscm_softc *sc = qcscm_sc;
uint64_t res[3];
uint64_t args[1];
uint32_t arginfo;
int ret;
if (sc == NULL)
return ENXIO;
arginfo = QCSCM_ARGINFO_NUM(nitems(args));
arginfo |= QCSCM_ARGINFO_TYPE(0, QCSCM_ARGINFO_TYPE_VAL);
args[0] = peripheral;
/* Make call into TEE */
ret = qcscm_smc_call(sc, ARM_SMCCC_OWNER_SIP, QCSCM_SVC_PIL,
QCSCM_PIL_PAS_AUTH_AND_RESET, arginfo, args, nitems(args), res);
/* If the call succeeded, check the response status */
if (ret == 0)
ret = res[0];
return ret;
}
/* DMA code */ /* DMA code */
struct qcscm_dmamem * struct qcscm_dmamem *
qcscm_dmamem_alloc(struct qcscm_softc *sc, bus_size_t size, bus_size_t align) qcscm_dmamem_alloc(struct qcscm_softc *sc, bus_size_t size, bus_size_t align)

View file

@ -1,4 +1,4 @@
/* $OpenBSD: ofw_misc.c,v 1.42 2023/04/26 21:37:46 patrick Exp $ */ /* $OpenBSD: ofw_misc.c,v 1.43 2023/05/17 23:25:45 patrick Exp $ */
/* /*
* Copyright (c) 2017-2021 Mark Kettenis * Copyright (c) 2017-2021 Mark Kettenis
* *
@ -1344,3 +1344,108 @@ mbox_recv(struct mbox_channel *mc, void *data, size_t len)
return ENXIO; return ENXIO;
} }
/* hwlock support */
LIST_HEAD(, hwlock_device) hwlock_devices =
LIST_HEAD_INITIALIZER(hwlock_devices);
void
hwlock_register(struct hwlock_device *hd)
{
hd->hd_cells = OF_getpropint(hd->hd_node, "#hwlock-cells", 0);
hd->hd_phandle = OF_getpropint(hd->hd_node, "phandle", 0);
if (hd->hd_phandle == 0)
return;
LIST_INSERT_HEAD(&hwlock_devices, hd, hd_list);
}
int
hwlock_lock_cells(uint32_t *cells, int lock)
{
struct hwlock_device *hd;
uint32_t phandle = cells[0];
LIST_FOREACH(hd, &hwlock_devices, hd_list) {
if (hd->hd_phandle == phandle)
break;
}
if (hd && hd->hd_lock)
return hd->hd_lock(hd->hd_cookie, &cells[1], lock);
return ENXIO;
}
uint32_t *
hwlock_next_hwlock(uint32_t *cells)
{
uint32_t phandle = cells[0];
int node, ncells;
node = OF_getnodebyphandle(phandle);
if (node == 0)
return NULL;
ncells = OF_getpropint(node, "#hwlock-cells", 0);
return cells + ncells + 1;
}
int
hwlock_do_lock_idx(int node, int idx, int lock)
{
uint32_t *hwlocks;
uint32_t *hwlock;
int rv = -1;
int len;
len = OF_getproplen(node, "hwlocks");
if (len <= 0)
return -1;
hwlocks = malloc(len, M_TEMP, M_WAITOK);
OF_getpropintarray(node, "hwlocks", hwlocks, len);
hwlock = hwlocks;
while (hwlock && hwlock < hwlocks + (len / sizeof(uint32_t))) {
if (idx <= 0)
rv = hwlock_lock_cells(hwlock, lock);
if (idx == 0)
break;
hwlock = hwlock_next_hwlock(hwlock);
idx--;
}
free(hwlocks, M_TEMP, len);
return rv;
}
int
hwlock_lock_idx(int node, int idx)
{
return hwlock_do_lock_idx(node, idx, 1);
}
int
hwlock_lock_idx_timeout(int node, int idx, int ms)
{
int i, ret = ENXIO;
for (i = 0; i <= ms; i++) {
ret = hwlock_do_lock_idx(node, idx, 1);
if (ret == EAGAIN) {
delay(1000);
continue;
}
break;
}
return ret;
}
int
hwlock_unlock_idx(int node, int idx)
{
return hwlock_do_lock_idx(node, idx, 0);
}

View file

@ -1,4 +1,4 @@
/* $OpenBSD: ofw_misc.h,v 1.29 2023/04/03 01:40:32 dlg Exp $ */ /* $OpenBSD: ofw_misc.h,v 1.30 2023/05/17 23:25:45 patrick Exp $ */
/* /*
* Copyright (c) 2017-2021 Mark Kettenis * Copyright (c) 2017-2021 Mark Kettenis
* *
@ -313,4 +313,22 @@ struct mbox_channel *mbox_channel_idx(int, int, struct mbox_client *);
int mbox_send(struct mbox_channel *, const void *, size_t); int mbox_send(struct mbox_channel *, const void *, size_t);
int mbox_recv(struct mbox_channel *, void *, size_t); int mbox_recv(struct mbox_channel *, void *, size_t);
/* hwlock support */
struct hwlock_device {
int hd_node;
void *hd_cookie;
int (*hd_lock)(void *, uint32_t *, int);
LIST_ENTRY(hwlock_device) hd_list;
uint32_t hd_phandle;
uint32_t hd_cells;
};
void hwlock_register(struct hwlock_device *);
int hwlock_lock_idx(int, int);
int hwlock_lock_idx_timeout(int, int, int);
int hwlock_unlock_idx(int, int);
#endif /* _DEV_OFW_MISC_H_ */ #endif /* _DEV_OFW_MISC_H_ */

View file

@ -1,4 +1,4 @@
/* $OpenBSD: if_ix.c,v 1.194 2023/05/16 14:32:54 jan Exp $ */ /* $OpenBSD: if_ix.c,v 1.195 2023/05/18 08:22:37 jan Exp $ */
/****************************************************************************** /******************************************************************************
@ -1924,6 +1924,7 @@ ixgbe_setup_interface(struct ix_softc *sc)
ifp->if_capabilities |= IFCAP_CSUM_TCPv6 | IFCAP_CSUM_UDPv6; ifp->if_capabilities |= IFCAP_CSUM_TCPv6 | IFCAP_CSUM_UDPv6;
ifp->if_capabilities |= IFCAP_CSUM_IPv4; ifp->if_capabilities |= IFCAP_CSUM_IPv4;
ifp->if_capabilities |= IFCAP_TSOv4 | IFCAP_TSOv6;
if (sc->hw.mac.type != ixgbe_mac_82598EB) if (sc->hw.mac.type != ixgbe_mac_82598EB)
ifp->if_capabilities |= IFCAP_LRO; ifp->if_capabilities |= IFCAP_LRO;
@ -2344,6 +2345,7 @@ ixgbe_initialize_transmit_units(struct ix_softc *sc)
int i; int i;
uint64_t tdba; uint64_t tdba;
uint32_t txctrl; uint32_t txctrl;
uint32_t hlreg;
/* Setup the Base and Length of the Tx Descriptor Ring */ /* Setup the Base and Length of the Tx Descriptor Ring */
@ -2405,6 +2407,11 @@ ixgbe_initialize_transmit_units(struct ix_softc *sc)
rttdcs &= ~IXGBE_RTTDCS_ARBDIS; rttdcs &= ~IXGBE_RTTDCS_ARBDIS;
IXGBE_WRITE_REG(hw, IXGBE_RTTDCS, rttdcs); IXGBE_WRITE_REG(hw, IXGBE_RTTDCS, rttdcs);
} }
/* Enable TCP/UDP padding when using TSO */
hlreg = IXGBE_READ_REG(hw, IXGBE_HLREG0);
hlreg |= IXGBE_HLREG0_TXPADEN;
IXGBE_WRITE_REG(hw, IXGBE_HLREG0, hlreg);
} }
/********************************************************************* /*********************************************************************
@ -2473,16 +2480,18 @@ ixgbe_free_transmit_buffers(struct tx_ring *txr)
**********************************************************************/ **********************************************************************/
static inline int static inline int
ixgbe_csum_offload(struct mbuf *mp, uint32_t *vlan_macip_lens, ixgbe_tx_offload(struct mbuf *mp, uint32_t *vlan_macip_lens,
uint32_t *type_tucmd_mlhl, uint32_t *olinfo_status) uint32_t *type_tucmd_mlhl, uint32_t *olinfo_status, uint32_t *cmd_type_len,
uint32_t *mss_l4len_idx)
{ {
struct ether_extracted ext; struct ether_extracted ext;
int offload = 0; int offload = 0;
uint32_t iphlen; uint32_t ethlen, iphlen;
ether_extract_headers(mp, &ext); ether_extract_headers(mp, &ext);
ethlen = sizeof(*ext.eh);
*vlan_macip_lens |= (sizeof(*ext.eh) << IXGBE_ADVTXD_MACLEN_SHIFT); *vlan_macip_lens |= (ethlen << IXGBE_ADVTXD_MACLEN_SHIFT);
if (ext.ip4) { if (ext.ip4) {
iphlen = ext.ip4->ip_hl << 2; iphlen = ext.ip4->ip_hl << 2;
@ -2500,6 +2509,8 @@ ixgbe_csum_offload(struct mbuf *mp, uint32_t *vlan_macip_lens,
*type_tucmd_mlhl |= IXGBE_ADVTXD_TUCMD_IPV6; *type_tucmd_mlhl |= IXGBE_ADVTXD_TUCMD_IPV6;
#endif #endif
} else { } else {
if (mp->m_pkthdr.csum_flags & M_TCP_TSO)
tcpstat_inc(tcps_outbadtso);
return offload; return offload;
} }
@ -2519,6 +2530,31 @@ ixgbe_csum_offload(struct mbuf *mp, uint32_t *vlan_macip_lens,
} }
} }
if (mp->m_pkthdr.csum_flags & M_TCP_TSO) {
if (ext.tcp) {
uint32_t hdrlen, thlen, paylen, outlen;
thlen = ext.tcp->th_off << 2;
outlen = mp->m_pkthdr.ph_mss;
*mss_l4len_idx |= outlen << IXGBE_ADVTXD_MSS_SHIFT;
*mss_l4len_idx |= thlen << IXGBE_ADVTXD_L4LEN_SHIFT;
hdrlen = ethlen + iphlen + thlen;
paylen = mp->m_pkthdr.len - hdrlen;
CLR(*olinfo_status, IXGBE_ADVTXD_PAYLEN_MASK
<< IXGBE_ADVTXD_PAYLEN_SHIFT);
*olinfo_status |= paylen << IXGBE_ADVTXD_PAYLEN_SHIFT;
*cmd_type_len |= IXGBE_ADVTXD_DCMD_TSE;
offload = 1;
tcpstat_add(tcps_outpkttso,
(paylen + outlen - 1) / outlen);
} else
tcpstat_inc(tcps_outbadtso);
}
return offload; return offload;
} }
@ -2529,6 +2565,7 @@ ixgbe_tx_ctx_setup(struct tx_ring *txr, struct mbuf *mp,
struct ixgbe_adv_tx_context_desc *TXD; struct ixgbe_adv_tx_context_desc *TXD;
struct ixgbe_tx_buf *tx_buffer; struct ixgbe_tx_buf *tx_buffer;
uint32_t vlan_macip_lens = 0, type_tucmd_mlhl = 0; uint32_t vlan_macip_lens = 0, type_tucmd_mlhl = 0;
uint32_t mss_l4len_idx = 0;
int ctxd = txr->next_avail_desc; int ctxd = txr->next_avail_desc;
int offload = 0; int offload = 0;
@ -2544,8 +2581,8 @@ ixgbe_tx_ctx_setup(struct tx_ring *txr, struct mbuf *mp,
} }
#endif #endif
offload |= ixgbe_csum_offload(mp, &vlan_macip_lens, &type_tucmd_mlhl, offload |= ixgbe_tx_offload(mp, &vlan_macip_lens, &type_tucmd_mlhl,
olinfo_status); olinfo_status, cmd_type_len, &mss_l4len_idx);
if (!offload) if (!offload)
return (0); return (0);
@ -2559,7 +2596,7 @@ ixgbe_tx_ctx_setup(struct tx_ring *txr, struct mbuf *mp,
TXD->vlan_macip_lens = htole32(vlan_macip_lens); TXD->vlan_macip_lens = htole32(vlan_macip_lens);
TXD->type_tucmd_mlhl = htole32(type_tucmd_mlhl); TXD->type_tucmd_mlhl = htole32(type_tucmd_mlhl);
TXD->seqnum_seed = htole32(0); TXD->seqnum_seed = htole32(0);
TXD->mss_l4len_idx = htole32(0); TXD->mss_l4len_idx = htole32(mss_l4len_idx);
tx_buffer->m_head = NULL; tx_buffer->m_head = NULL;
tx_buffer->eop_index = -1; tx_buffer->eop_index = -1;
@ -2868,9 +2905,11 @@ ixgbe_initialize_receive_units(struct ix_softc *sc)
} }
IXGBE_WRITE_REG(hw, IXGBE_FCTRL, fctrl); IXGBE_WRITE_REG(hw, IXGBE_FCTRL, fctrl);
/* Always enable jumbo frame reception */
hlreg = IXGBE_READ_REG(hw, IXGBE_HLREG0); hlreg = IXGBE_READ_REG(hw, IXGBE_HLREG0);
/* Always enable jumbo frame reception */
hlreg |= IXGBE_HLREG0_JUMBOEN; hlreg |= IXGBE_HLREG0_JUMBOEN;
/* Always enable CRC stripping */
hlreg |= IXGBE_HLREG0_RXCRCSTRP;
IXGBE_WRITE_REG(hw, IXGBE_HLREG0, hlreg); IXGBE_WRITE_REG(hw, IXGBE_HLREG0, hlreg);
if (ISSET(ifp->if_xflags, IFXF_LRO)) { if (ISSET(ifp->if_xflags, IFXF_LRO)) {

View file

@ -1,4 +1,4 @@
/* $OpenBSD: ixgbe.h,v 1.33 2022/02/08 03:38:00 dlg Exp $ */ /* $OpenBSD: ixgbe.h,v 1.34 2023/05/18 08:22:37 jan Exp $ */
/****************************************************************************** /******************************************************************************
@ -60,12 +60,16 @@
#include <net/if.h> #include <net/if.h>
#include <net/if_media.h> #include <net/if_media.h>
#include <net/route.h>
#include <net/toeplitz.h> #include <net/toeplitz.h>
#include <netinet/in.h> #include <netinet/in.h>
#include <netinet/if_ether.h> #include <netinet/if_ether.h>
#include <netinet/ip.h> #include <netinet/ip.h>
#include <netinet/ip6.h> #include <netinet/ip6.h>
#include <netinet/tcp.h>
#include <netinet/tcp_timer.h>
#include <netinet/tcp_var.h>
#if NBPFILTER > 0 #if NBPFILTER > 0
#include <net/bpf.h> #include <net/bpf.h>

View file

@ -1,4 +1,4 @@
/* $OpenBSD: ixgbe_type.h,v 1.36 2022/01/09 05:42:56 jsg Exp $ */ /* $OpenBSD: ixgbe_type.h,v 1.37 2023/05/18 08:22:37 jan Exp $ */
/****************************************************************************** /******************************************************************************
SPDX-License-Identifier: BSD-3-Clause SPDX-License-Identifier: BSD-3-Clause
@ -3355,6 +3355,7 @@ struct ixgbe_adv_tx_context_desc {
/* 1st&Last TSO-full iSCSI PDU */ /* 1st&Last TSO-full iSCSI PDU */
#define IXGBE_ADVTXD_POPTS_ISCO_FULL 0x00001800 #define IXGBE_ADVTXD_POPTS_ISCO_FULL 0x00001800
#define IXGBE_ADVTXD_POPTS_RSV 0x00002000 /* POPTS Reserved */ #define IXGBE_ADVTXD_POPTS_RSV 0x00002000 /* POPTS Reserved */
#define IXGBE_ADVTXD_PAYLEN_MASK 0x0003FFFF /* Adv desc PAYLEN */
#define IXGBE_ADVTXD_PAYLEN_SHIFT 14 /* Adv desc PAYLEN shift */ #define IXGBE_ADVTXD_PAYLEN_SHIFT 14 /* Adv desc PAYLEN shift */
#define IXGBE_ADVTXD_MACLEN_SHIFT 9 /* Adv ctxt desc mac len shift */ #define IXGBE_ADVTXD_MACLEN_SHIFT 9 /* Adv ctxt desc mac len shift */
#define IXGBE_ADVTXD_VLAN_SHIFT 16 /* Adv ctxt vlan tag shift */ #define IXGBE_ADVTXD_VLAN_SHIFT 16 /* Adv ctxt vlan tag shift */

View file

@ -1,10 +1,10 @@
/* $OpenBSD: init_sysent.c,v 1.265 2023/05/04 09:41:15 mvs Exp $ */ /* $OpenBSD: init_sysent.c,v 1.266 2023/05/18 10:24:28 mvs Exp $ */
/* /*
* System call switch table. * System call switch table.
* *
* DO NOT EDIT-- this file is automatically generated. * DO NOT EDIT-- this file is automatically generated.
* created from; OpenBSD: syscalls.master,v 1.247 2023/05/04 09:40:36 mvs Exp * created from; OpenBSD: syscalls.master,v 1.248 2023/05/18 10:23:19 mvs Exp
*/ */
#include <sys/param.h> #include <sys/param.h>
@ -441,7 +441,7 @@ const struct sysent sysent[] = {
sys_nosys }, /* 200 = obsolete pad_truncate */ sys_nosys }, /* 200 = obsolete pad_truncate */
{ 0, 0, 0, { 0, 0, 0,
sys_nosys }, /* 201 = obsolete pad_ftruncate */ sys_nosys }, /* 201 = obsolete pad_ftruncate */
{ 6, s(struct sys_sysctl_args), SY_NOLOCK | 0, { 6, s(struct sys_sysctl_args), 0,
sys_sysctl }, /* 202 = sysctl */ sys_sysctl }, /* 202 = sysctl */
{ 2, s(struct sys_mlock_args), 0, { 2, s(struct sys_mlock_args), 0,
sys_mlock }, /* 203 = mlock */ sys_mlock }, /* 203 = mlock */

View file

@ -1,4 +1,4 @@
/* $OpenBSD: kern_sysctl.c,v 1.412 2023/05/04 09:40:36 mvs Exp $ */ /* $OpenBSD: kern_sysctl.c,v 1.414 2023/05/18 10:23:19 mvs Exp $ */
/* $NetBSD: kern_sysctl.c,v 1.17 1996/05/20 17:49:05 mrg Exp $ */ /* $NetBSD: kern_sysctl.c,v 1.17 1996/05/20 17:49:05 mrg Exp $ */
/*- /*-
@ -143,6 +143,7 @@ int sysctl_audio(int *, u_int, void *, size_t *, void *, size_t);
int sysctl_video(int *, u_int, void *, size_t *, void *, size_t); int sysctl_video(int *, u_int, void *, size_t *, void *, size_t);
int sysctl_cpustats(int *, u_int, void *, size_t *, void *, size_t); int sysctl_cpustats(int *, u_int, void *, size_t *, void *, size_t);
int sysctl_utc_offset(void *, size_t *, void *, size_t); int sysctl_utc_offset(void *, size_t *, void *, size_t);
int sysctl_hwbattery(int *, u_int, void *, size_t *, void *, size_t);
void fill_file(struct kinfo_file *, struct file *, struct filedesc *, int, void fill_file(struct kinfo_file *, struct file *, struct filedesc *, int,
struct vnode *, struct process *, struct proc *, struct socket *, int); struct vnode *, struct process *, struct proc *, struct socket *, int);
@ -168,7 +169,7 @@ sys_sysctl(struct proc *p, void *v, register_t *retval)
syscallarg(void *) new; syscallarg(void *) new;
syscallarg(size_t) newlen; syscallarg(size_t) newlen;
} */ *uap = v; } */ *uap = v;
int error, dokernellock = 1, dolock = 1; int error, dolock = 1;
size_t savelen = 0, oldlen = 0; size_t savelen = 0, oldlen = 0;
sysctlfn *fn; sysctlfn *fn;
int name[CTL_MAXNAME]; int name[CTL_MAXNAME];
@ -203,7 +204,6 @@ sys_sysctl(struct proc *p, void *v, register_t *retval)
break; break;
case CTL_NET: case CTL_NET:
fn = net_sysctl; fn = net_sysctl;
dokernellock = 0;
break; break;
case CTL_FS: case CTL_FS:
fn = fs_sysctl; fn = fs_sysctl;
@ -231,22 +231,19 @@ sys_sysctl(struct proc *p, void *v, register_t *retval)
if (SCARG(uap, oldlenp) && if (SCARG(uap, oldlenp) &&
(error = copyin(SCARG(uap, oldlenp), &oldlen, sizeof(oldlen)))) (error = copyin(SCARG(uap, oldlenp), &oldlen, sizeof(oldlen))))
return (error); return (error);
if (dokernellock)
KERNEL_LOCK();
if (SCARG(uap, old) != NULL) { if (SCARG(uap, old) != NULL) {
if ((error = rw_enter(&sysctl_lock, RW_WRITE|RW_INTR)) != 0) if ((error = rw_enter(&sysctl_lock, RW_WRITE|RW_INTR)) != 0)
goto unlock; return (error);
if (dolock) { if (dolock) {
if (atop(oldlen) > uvmexp.wiredmax - uvmexp.wired) { if (atop(oldlen) > uvmexp.wiredmax - uvmexp.wired) {
rw_exit_write(&sysctl_lock); rw_exit_write(&sysctl_lock);
error = ENOMEM; return (ENOMEM);
goto unlock;
} }
error = uvm_vslock(p, SCARG(uap, old), oldlen, error = uvm_vslock(p, SCARG(uap, old), oldlen,
PROT_READ | PROT_WRITE); PROT_READ | PROT_WRITE);
if (error) { if (error) {
rw_exit_write(&sysctl_lock); rw_exit_write(&sysctl_lock);
goto unlock; return (error);
} }
} }
savelen = oldlen; savelen = oldlen;
@ -258,9 +255,6 @@ sys_sysctl(struct proc *p, void *v, register_t *retval)
uvm_vsunlock(p, SCARG(uap, old), savelen); uvm_vsunlock(p, SCARG(uap, old), savelen);
rw_exit_write(&sysctl_lock); rw_exit_write(&sysctl_lock);
} }
unlock:
if (dokernellock)
KERNEL_UNLOCK();
if (error) if (error)
return (error); return (error);
if (SCARG(uap, oldlenp)) if (SCARG(uap, oldlenp))
@ -689,8 +683,11 @@ hw_sysctl(int *name, u_int namelen, void *oldp, size_t *oldlenp, void *newp,
extern char machine[], cpu_model[]; extern char machine[], cpu_model[];
int err, cpuspeed; int err, cpuspeed;
/* all sysctl names at this level except sensors are terminal */ /*
if (name[0] != HW_SENSORS && namelen != 1) * all sysctl names at this level except sensors and battery
* are terminal
*/
if (name[0] != HW_SENSORS && name[0] != HW_BATTERY && namelen != 1)
return (ENOTDIR); /* overloaded */ return (ENOTDIR); /* overloaded */
switch (name[0]) { switch (name[0]) {
@ -776,6 +773,11 @@ hw_sysctl(int *name, u_int namelen, void *oldp, size_t *oldlenp, void *newp,
#ifdef __HAVE_CPU_TOPOLOGY #ifdef __HAVE_CPU_TOPOLOGY
case HW_SMT: case HW_SMT:
return (sysctl_hwsmt(oldp, oldlenp, newp, newlen)); return (sysctl_hwsmt(oldp, oldlenp, newp, newlen));
#endif
#ifndef SMALL_KERNEL
case HW_BATTERY:
return (sysctl_hwbattery(name + 1, namelen - 1, oldp, oldlenp,
newp, newlen));
#endif #endif
default: default:
return sysctl_bounded_arr(hw_vars, nitems(hw_vars), name, return sysctl_bounded_arr(hw_vars, nitems(hw_vars), name,
@ -784,6 +786,97 @@ hw_sysctl(int *name, u_int namelen, void *oldp, size_t *oldlenp, void *newp,
/* NOTREACHED */ /* NOTREACHED */
} }
#ifndef SMALL_KERNEL
int hw_battery_chargemode;
int hw_battery_chargestart;
int hw_battery_chargestop;
int (*hw_battery_setchargemode)(int);
int (*hw_battery_setchargestart)(int);
int (*hw_battery_setchargestop)(int);
int
sysctl_hwchargemode(void *oldp, size_t *oldlenp, void *newp, size_t newlen)
{
int mode = hw_battery_chargemode;
int error;
if (!hw_battery_setchargemode)
return EOPNOTSUPP;
error = sysctl_int_bounded(oldp, oldlenp, newp, newlen,
&mode, -1, 1);
if (error)
return error;
if (newp != NULL)
error = hw_battery_setchargemode(mode);
return error;
}
int
sysctl_hwchargestart(void *oldp, size_t *oldlenp, void *newp, size_t newlen)
{
int start = hw_battery_chargestart;
int error;
if (!hw_battery_setchargestart)
return EOPNOTSUPP;
error = sysctl_int_bounded(oldp, oldlenp, newp, newlen,
&start, 0, 100);
if (error)
return error;
if (newp != NULL)
error = hw_battery_setchargestart(start);
return error;
}
int
sysctl_hwchargestop(void *oldp, size_t *oldlenp, void *newp, size_t newlen)
{
int stop = hw_battery_chargestop;
int error;
if (!hw_battery_setchargestart)
return EOPNOTSUPP;
error = sysctl_int_bounded(oldp, oldlenp, newp, newlen,
&stop, 0, 100);
if (error)
return error;
if (newp != NULL)
error = hw_battery_setchargestop(stop);
return error;
}
int
sysctl_hwbattery(int *name, u_int namelen, void *oldp, size_t *oldlenp,
void *newp, size_t newlen)
{
if (namelen != 1)
return (ENOTDIR);
switch (name[0]) {
case HW_BATTERY_CHARGEMODE:
return (sysctl_hwchargemode(oldp, oldlenp, newp, newlen));
case HW_BATTERY_CHARGESTART:
return (sysctl_hwchargestart(oldp, oldlenp, newp, newlen));
case HW_BATTERY_CHARGESTOP:
return (sysctl_hwchargestop(oldp, oldlenp, newp, newlen));
default:
return (EOPNOTSUPP);
}
/* NOTREACHED */
}
#endif
#ifdef DEBUG_SYSCTL #ifdef DEBUG_SYSCTL
/* /*
* Debugging related system variables. * Debugging related system variables.

View file

@ -1,10 +1,10 @@
/* $OpenBSD: syscalls.c,v 1.263 2023/05/04 09:41:15 mvs Exp $ */ /* $OpenBSD: syscalls.c,v 1.264 2023/05/18 10:24:28 mvs Exp $ */
/* /*
* System call names. * System call names.
* *
* DO NOT EDIT-- this file is automatically generated. * DO NOT EDIT-- this file is automatically generated.
* created from; OpenBSD: syscalls.master,v 1.247 2023/05/04 09:40:36 mvs Exp * created from; OpenBSD: syscalls.master,v 1.248 2023/05/18 10:23:19 mvs Exp
*/ */
const char *const syscallnames[] = { const char *const syscallnames[] = {

View file

@ -1,4 +1,4 @@
; $OpenBSD: syscalls.master,v 1.247 2023/05/04 09:40:36 mvs Exp $ ; $OpenBSD: syscalls.master,v 1.248 2023/05/18 10:23:19 mvs Exp $
; $NetBSD: syscalls.master,v 1.32 1996/04/23 10:24:21 mycroft Exp $ ; $NetBSD: syscalls.master,v 1.32 1996/04/23 10:24:21 mycroft Exp $
; @(#)syscalls.master 8.2 (Berkeley) 1/13/94 ; @(#)syscalls.master 8.2 (Berkeley) 1/13/94
@ -361,7 +361,7 @@
199 OBSOL pad_lseek 199 OBSOL pad_lseek
200 OBSOL pad_truncate 200 OBSOL pad_truncate
201 OBSOL pad_ftruncate 201 OBSOL pad_ftruncate
202 STD NOLOCK { int sys_sysctl(const int *name, u_int namelen, \ 202 STD { int sys_sysctl(const int *name, u_int namelen, \
void *old, size_t *oldlenp, void *new, \ void *old, size_t *oldlenp, void *new, \
size_t newlen); } size_t newlen); }
203 STD { int sys_mlock(const void *addr, size_t len); } 203 STD { int sys_mlock(const void *addr, size_t len); }

View file

@ -1,4 +1,4 @@
/* $OpenBSD: uipc_domain.c,v 1.62 2023/05/16 19:36:00 mvs Exp $ */ /* $OpenBSD: uipc_domain.c,v 1.64 2023/05/18 10:23:19 mvs Exp $ */
/* $NetBSD: uipc_domain.c,v 1.14 1996/02/09 19:00:44 christos Exp $ */ /* $NetBSD: uipc_domain.c,v 1.14 1996/02/09 19:00:44 christos Exp $ */
/* /*
@ -188,7 +188,7 @@ net_sysctl(int *name, u_int namelen, void *oldp, size_t *oldlenp, void *newp,
{ {
const struct domain *dp; const struct domain *dp;
const struct protosw *pr; const struct protosw *pr;
int error, family, protocol; int family, protocol;
/* /*
* All sysctl names at this level are nonterminal. * All sysctl names at this level are nonterminal.
@ -213,13 +213,9 @@ net_sysctl(int *name, u_int namelen, void *oldp, size_t *oldlenp, void *newp,
newp, newlen)); newp, newlen));
#endif #endif
#if NPFLOW > 0 #if NPFLOW > 0
if (family == PF_PFLOW) { if (family == PF_PFLOW)
KERNEL_LOCK(); return (pflow_sysctl(name + 1, namelen - 1, oldp, oldlenp,
error = pflow_sysctl(name + 1, namelen - 1, oldp, oldlenp, newp, newlen));
newp, newlen);
KERNEL_UNLOCK();
return (error);
}
#endif #endif
#ifdef PIPEX #ifdef PIPEX
if (family == PF_PIPEX) if (family == PF_PIPEX)
@ -227,13 +223,9 @@ net_sysctl(int *name, u_int namelen, void *oldp, size_t *oldlenp, void *newp,
newp, newlen)); newp, newlen));
#endif #endif
#ifdef MPLS #ifdef MPLS
if (family == PF_MPLS) { if (family == PF_MPLS)
KERNEL_LOCK(); return (mpls_sysctl(name + 1, namelen - 1, oldp, oldlenp,
error = mpls_sysctl(name + 1, namelen - 1, oldp, oldlenp, newp, newlen));
newp, newlen);
KERNEL_UNLOCK();
return (error);
}
#endif #endif
dp = pffinddomain(family); dp = pffinddomain(family);
if (dp == NULL) if (dp == NULL)
@ -243,15 +235,9 @@ net_sysctl(int *name, u_int namelen, void *oldp, size_t *oldlenp, void *newp,
return (EISDIR); /* overloaded */ return (EISDIR); /* overloaded */
protocol = name[1]; protocol = name[1];
for (pr = dp->dom_protosw; pr < dp->dom_protoswNPROTOSW; pr++) for (pr = dp->dom_protosw; pr < dp->dom_protoswNPROTOSW; pr++)
if (pr->pr_protocol == protocol && pr->pr_sysctl) { if (pr->pr_protocol == protocol && pr->pr_sysctl)
if ((pr->pr_flags & PR_MPSYSCTL) == 0) return ((*pr->pr_sysctl)(name + 2, namelen - 2,
KERNEL_LOCK(); oldp, oldlenp, newp, newlen));
error = (*pr->pr_sysctl)(name + 2, namelen - 2,
oldp, oldlenp, newp, newlen);
if ((pr->pr_flags & PR_MPSYSCTL) == 0)
KERNEL_UNLOCK();
return (error);
}
return (ENOPROTOOPT); return (ENOPROTOOPT);
} }

View file

@ -1,4 +1,4 @@
/* $OpenBSD: if_pfsync.c,v 1.314 2023/04/28 15:50:05 sashan Exp $ */ /* $OpenBSD: if_pfsync.c,v 1.315 2023/05/18 12:10:04 sashan Exp $ */
/* /*
* Copyright (c) 2002 Michael Shalayeff * Copyright (c) 2002 Michael Shalayeff
@ -1362,14 +1362,17 @@ pfsync_grab_snapshot(struct pfsync_snapshot *sn, struct pfsync_softc *sc)
while ((st = TAILQ_FIRST(&sc->sc_qs[q])) != NULL) { while ((st = TAILQ_FIRST(&sc->sc_qs[q])) != NULL) {
TAILQ_REMOVE(&sc->sc_qs[q], st, sync_list); TAILQ_REMOVE(&sc->sc_qs[q], st, sync_list);
mtx_enter(&st->mtx);
if (st->snapped == 0) { if (st->snapped == 0) {
TAILQ_INSERT_TAIL(&sn->sn_qs[q], st, sync_snap); TAILQ_INSERT_TAIL(&sn->sn_qs[q], st, sync_snap);
st->snapped = 1; st->snapped = 1;
mtx_leave(&st->mtx);
} else { } else {
/* /*
* item is on snapshot list already, so we can * item is on snapshot list already, so we can
* skip it now. * skip it now.
*/ */
mtx_leave(&st->mtx);
pf_state_unref(st); pf_state_unref(st);
} }
} }
@ -1422,11 +1425,13 @@ pfsync_drop_snapshot(struct pfsync_snapshot *sn)
continue; continue;
while ((st = TAILQ_FIRST(&sn->sn_qs[q])) != NULL) { while ((st = TAILQ_FIRST(&sn->sn_qs[q])) != NULL) {
mtx_enter(&st->mtx);
KASSERT(st->sync_state == q); KASSERT(st->sync_state == q);
KASSERT(st->snapped == 1); KASSERT(st->snapped == 1);
TAILQ_REMOVE(&sn->sn_qs[q], st, sync_snap); TAILQ_REMOVE(&sn->sn_qs[q], st, sync_snap);
st->sync_state = PFSYNC_S_NONE; st->sync_state = PFSYNC_S_NONE;
st->snapped = 0; st->snapped = 0;
mtx_leave(&st->mtx);
pf_state_unref(st); pf_state_unref(st);
} }
} }
@ -1665,6 +1670,7 @@ pfsync_sendout(void)
count = 0; count = 0;
while ((st = TAILQ_FIRST(&sn.sn_qs[q])) != NULL) { while ((st = TAILQ_FIRST(&sn.sn_qs[q])) != NULL) {
mtx_enter(&st->mtx);
TAILQ_REMOVE(&sn.sn_qs[q], st, sync_snap); TAILQ_REMOVE(&sn.sn_qs[q], st, sync_snap);
KASSERT(st->sync_state == q); KASSERT(st->sync_state == q);
KASSERT(st->snapped == 1); KASSERT(st->snapped == 1);
@ -1672,6 +1678,7 @@ pfsync_sendout(void)
st->snapped = 0; st->snapped = 0;
pfsync_qs[q].write(st, m->m_data + offset); pfsync_qs[q].write(st, m->m_data + offset);
offset += pfsync_qs[q].len; offset += pfsync_qs[q].len;
mtx_leave(&st->mtx);
pf_state_unref(st); pf_state_unref(st);
count++; count++;
@ -1725,8 +1732,6 @@ pfsync_insert_state(struct pf_state *st)
ISSET(st->state_flags, PFSTATE_NOSYNC)) ISSET(st->state_flags, PFSTATE_NOSYNC))
return; return;
KASSERT(st->sync_state == PFSYNC_S_NONE);
if (sc->sc_len == PFSYNC_MINPKT) if (sc->sc_len == PFSYNC_MINPKT)
timeout_add_sec(&sc->sc_tmo, 1); timeout_add_sec(&sc->sc_tmo, 1);
@ -2221,6 +2226,7 @@ pfsync_q_ins(struct pf_state *st, int q)
panic("pfsync pkt len is too low %zd", sc->sc_len); panic("pfsync pkt len is too low %zd", sc->sc_len);
do { do {
mtx_enter(&sc->sc_st_mtx); mtx_enter(&sc->sc_st_mtx);
mtx_enter(&st->mtx);
/* /*
* There are either two threads trying to update the * There are either two threads trying to update the
@ -2228,6 +2234,7 @@ pfsync_q_ins(struct pf_state *st, int q)
* (is on snapshot queue). * (is on snapshot queue).
*/ */
if (st->sync_state != PFSYNC_S_NONE) { if (st->sync_state != PFSYNC_S_NONE) {
mtx_leave(&st->mtx);
mtx_leave(&sc->sc_st_mtx); mtx_leave(&sc->sc_st_mtx);
break; break;
} }
@ -2240,6 +2247,7 @@ pfsync_q_ins(struct pf_state *st, int q)
sclen = atomic_add_long_nv(&sc->sc_len, nlen); sclen = atomic_add_long_nv(&sc->sc_len, nlen);
if (sclen > sc->sc_if.if_mtu) { if (sclen > sc->sc_if.if_mtu) {
atomic_sub_long(&sc->sc_len, nlen); atomic_sub_long(&sc->sc_len, nlen);
mtx_leave(&st->mtx);
mtx_leave(&sc->sc_st_mtx); mtx_leave(&sc->sc_st_mtx);
pfsync_sendout(); pfsync_sendout();
continue; continue;
@ -2249,6 +2257,7 @@ pfsync_q_ins(struct pf_state *st, int q)
TAILQ_INSERT_TAIL(&sc->sc_qs[q], st, sync_list); TAILQ_INSERT_TAIL(&sc->sc_qs[q], st, sync_list);
st->sync_state = q; st->sync_state = q;
mtx_leave(&st->mtx);
mtx_leave(&sc->sc_st_mtx); mtx_leave(&sc->sc_st_mtx);
} while (0); } while (0);
} }
@ -2260,6 +2269,7 @@ pfsync_q_del(struct pf_state *st)
int q; int q;
mtx_enter(&sc->sc_st_mtx); mtx_enter(&sc->sc_st_mtx);
mtx_enter(&st->mtx);
q = st->sync_state; q = st->sync_state;
/* /*
* re-check under mutex * re-check under mutex
@ -2267,6 +2277,7 @@ pfsync_q_del(struct pf_state *st)
* too late, the state is being just processed/dispatched to peer. * too late, the state is being just processed/dispatched to peer.
*/ */
if ((q == PFSYNC_S_NONE) || (st->snapped)) { if ((q == PFSYNC_S_NONE) || (st->snapped)) {
mtx_leave(&st->mtx);
mtx_leave(&sc->sc_st_mtx); mtx_leave(&sc->sc_st_mtx);
return; return;
} }
@ -2275,6 +2286,7 @@ pfsync_q_del(struct pf_state *st)
if (TAILQ_EMPTY(&sc->sc_qs[q])) if (TAILQ_EMPTY(&sc->sc_qs[q]))
atomic_sub_long(&sc->sc_len, sizeof (struct pfsync_subheader)); atomic_sub_long(&sc->sc_len, sizeof (struct pfsync_subheader));
st->sync_state = PFSYNC_S_NONE; st->sync_state = PFSYNC_S_NONE;
mtx_leave(&st->mtx);
mtx_leave(&sc->sc_st_mtx); mtx_leave(&sc->sc_st_mtx);
pf_state_unref(st); pf_state_unref(st);

View file

@ -1,4 +1,4 @@
/* $OpenBSD: pf_if.c,v 1.109 2022/11/22 22:28:40 sashan Exp $ */ /* $OpenBSD: pf_if.c,v 1.110 2023/05/18 14:11:18 kn Exp $ */
/* /*
* Copyright 2005 Henning Brauer <henning@openbsd.org> * Copyright 2005 Henning Brauer <henning@openbsd.org>
@ -157,6 +157,8 @@ pfi_kif_find(const char *kif_name)
{ {
struct pfi_kif_cmp s; struct pfi_kif_cmp s;
PF_ASSERT_LOCKED();
memset(&s, 0, sizeof(s)); memset(&s, 0, sizeof(s));
strlcpy(s.pfik_name, kif_name, sizeof(s.pfik_name)); strlcpy(s.pfik_name, kif_name, sizeof(s.pfik_name));
return (RB_FIND(pfi_ifhead, &pfi_ifs, (struct pfi_kif *)&s)); return (RB_FIND(pfi_ifhead, &pfi_ifs, (struct pfi_kif *)&s));
@ -167,6 +169,8 @@ pfi_kif_get(const char *kif_name, struct pfi_kif **prealloc)
{ {
struct pfi_kif *kif; struct pfi_kif *kif;
PF_ASSERT_LOCKED();
if ((kif = pfi_kif_find(kif_name))) if ((kif = pfi_kif_find(kif_name)))
return (kif); return (kif);
@ -187,6 +191,8 @@ pfi_kif_get(const char *kif_name, struct pfi_kif **prealloc)
void void
pfi_kif_ref(struct pfi_kif *kif, enum pfi_kif_refs what) pfi_kif_ref(struct pfi_kif *kif, enum pfi_kif_refs what)
{ {
PF_ASSERT_LOCKED();
switch (what) { switch (what) {
case PFI_KIF_REF_RULE: case PFI_KIF_REF_RULE:
kif->pfik_rules++; kif->pfik_rules++;
@ -214,6 +220,8 @@ pfi_kif_unref(struct pfi_kif *kif, enum pfi_kif_refs what)
if (kif == NULL) if (kif == NULL)
return; return;
PF_ASSERT_LOCKED();
switch (what) { switch (what) {
case PFI_KIF_REF_NONE: case PFI_KIF_REF_NONE:
break; break;
@ -801,6 +809,8 @@ pfi_skip_if(const char *filter, struct pfi_kif *p)
struct ifg_list *i; struct ifg_list *i;
int n; int n;
PF_ASSERT_LOCKED();
if (filter == NULL || !*filter) if (filter == NULL || !*filter)
return (0); return (0);
if (!strcmp(p->pfik_name, filter)) if (!strcmp(p->pfik_name, filter))
@ -823,6 +833,8 @@ pfi_set_flags(const char *name, int flags)
struct pfi_kif *p; struct pfi_kif *p;
size_t n; size_t n;
PF_ASSERT_LOCKED();
if (name != NULL && name[0] != '\0') { if (name != NULL && name[0] != '\0') {
p = pfi_kif_find(name); p = pfi_kif_find(name);
if (p == NULL) { if (p == NULL) {
@ -862,6 +874,8 @@ pfi_clear_flags(const char *name, int flags)
{ {
struct pfi_kif *p, *w; struct pfi_kif *p, *w;
PF_ASSERT_LOCKED();
if (name != NULL && name[0] != '\0') { if (name != NULL && name[0] != '\0') {
p = pfi_kif_find(name); p = pfi_kif_find(name);
if (p != NULL) { if (p != NULL) {
@ -899,6 +913,8 @@ pfi_xcommit(void)
struct ifnet *ifp; struct ifnet *ifp;
size_t n; size_t n;
PF_ASSERT_LOCKED();
RB_FOREACH(p, pfi_ifhead, &pfi_ifs) { RB_FOREACH(p, pfi_ifhead, &pfi_ifs) {
p->pfik_flags = p->pfik_flags_new; p->pfik_flags = p->pfik_flags_new;
n = strlen(p->pfik_name); n = strlen(p->pfik_name);

View file

@ -1,4 +1,4 @@
/* $OpenBSD: in_proto.c,v 1.100 2023/05/16 19:36:00 mvs Exp $ */ /* $OpenBSD: in_proto.c,v 1.101 2023/05/18 09:59:43 mvs Exp $ */
/* $NetBSD: in_proto.c,v 1.14 1996/02/18 18:58:32 christos Exp $ */ /* $NetBSD: in_proto.c,v 1.14 1996/02/18 18:58:32 christos Exp $ */
/* /*
@ -177,7 +177,6 @@ u_char ip_protox[IPPROTO_MAX];
const struct protosw inetsw[] = { const struct protosw inetsw[] = {
{ {
.pr_domain = &inetdomain, .pr_domain = &inetdomain,
.pr_flags = PR_MPSYSCTL,
.pr_init = ip_init, .pr_init = ip_init,
.pr_slowtimo = ip_slowtimo, .pr_slowtimo = ip_slowtimo,
.pr_sysctl = ip_sysctl .pr_sysctl = ip_sysctl

View file

@ -1,4 +1,4 @@
/* $OpenBSD: ip_input.c,v 1.384 2023/05/16 19:36:00 mvs Exp $ */ /* $OpenBSD: ip_input.c,v 1.385 2023/05/18 09:59:43 mvs Exp $ */
/* $NetBSD: ip_input.c,v 1.30 1996/03/16 23:53:58 christos Exp $ */ /* $NetBSD: ip_input.c,v 1.30 1996/03/16 23:53:58 christos Exp $ */
/* /*
@ -1704,11 +1704,8 @@ ip_sysctl(int *name, u_int namelen, void *oldp, size_t *oldlenp, void *newp,
return (ip_sysctl_ipstat(oldp, oldlenp, newp)); return (ip_sysctl_ipstat(oldp, oldlenp, newp));
#ifdef MROUTING #ifdef MROUTING
case IPCTL_MRTSTATS: case IPCTL_MRTSTATS:
KERNEL_LOCK(); return (sysctl_rdstruct(oldp, oldlenp, newp,
error = sysctl_rdstruct(oldp, oldlenp, newp, &mrtstat, sizeof(mrtstat)));
&mrtstat, sizeof(mrtstat));
KERNEL_UNLOCK();
return (error);
case IPCTL_MRTMFC: case IPCTL_MRTMFC:
if (newp) if (newp)
return (EPERM); return (EPERM);

View file

@ -1,4 +1,4 @@
/* $OpenBSD: tcp_var.h,v 1.165 2023/05/15 16:34:56 bluhm Exp $ */ /* $OpenBSD: tcp_var.h,v 1.166 2023/05/18 08:22:37 jan Exp $ */
/* $NetBSD: tcp_var.h,v 1.17 1996/02/13 23:44:24 christos Exp $ */ /* $NetBSD: tcp_var.h,v 1.17 1996/02/13 23:44:24 christos Exp $ */
/* /*
@ -688,6 +688,8 @@ extern int tcp_syn_use_limit; /* number of uses before reseeding hash */
extern struct syn_cache_set tcp_syn_cache[]; extern struct syn_cache_set tcp_syn_cache[];
extern int tcp_syn_cache_active; /* active syn cache, may be 0 or 1 */ extern int tcp_syn_cache_active; /* active syn cache, may be 0 or 1 */
struct tdb;
void tcp_canceltimers(struct tcpcb *); void tcp_canceltimers(struct tcpcb *);
struct tcpcb * struct tcpcb *
tcp_close(struct tcpcb *); tcp_close(struct tcpcb *);

View file

@ -1,4 +1,4 @@
/* $OpenBSD: device.h,v 1.64 2022/09/03 18:05:10 kettenis Exp $ */ /* $OpenBSD: device.h,v 1.65 2023/05/17 20:23:14 patrick Exp $ */
/* $NetBSD: device.h,v 1.15 1996/04/09 20:55:24 cgd Exp $ */ /* $NetBSD: device.h,v 1.15 1996/04/09 20:55:24 cgd Exp $ */
/* /*
@ -231,7 +231,7 @@ void device_register(struct device *, void *);
void device_register_wakeup(struct device *); void device_register_wakeup(struct device *);
int loadfirmware(const char *name, u_char **bufp, size_t *buflen); int loadfirmware(const char *name, u_char **bufp, size_t *buflen);
#define FIRMWARE_MAX 5*1024*1024 #define FIRMWARE_MAX 15*1024*1024
/* compatibility definitions */ /* compatibility definitions */
#define config_found(d, a, p) config_found_sm((d), (a), (p), NULL) #define config_found(d, a, p) config_found_sm((d), (a), (p), NULL)

View file

@ -1,4 +1,4 @@
/* $OpenBSD: protosw.h,v 1.61 2023/05/16 19:44:55 mvs Exp $ */ /* $OpenBSD: protosw.h,v 1.62 2023/05/18 09:59:44 mvs Exp $ */
/* $NetBSD: protosw.h,v 1.10 1996/04/09 20:55:32 cgd Exp $ */ /* $NetBSD: protosw.h,v 1.10 1996/04/09 20:55:32 cgd Exp $ */
/*- /*-
@ -131,8 +131,6 @@ struct protosw {
#define PR_ABRTACPTDIS 0x0020 /* abort on accept(2) to disconnected #define PR_ABRTACPTDIS 0x0020 /* abort on accept(2) to disconnected
socket */ socket */
#define PR_SPLICE 0x0040 /* socket splicing is possible */ #define PR_SPLICE 0x0040 /* socket splicing is possible */
#define PR_MPSYSCTL 0x0080 /* (*pr_sysctl)() doesn't require
kernel lock */
/* /*
* The arguments to usrreq are: * The arguments to usrreq are:

View file

@ -1,10 +1,10 @@
/* $OpenBSD: syscall.h,v 1.262 2023/05/04 09:41:15 mvs Exp $ */ /* $OpenBSD: syscall.h,v 1.263 2023/05/18 10:24:28 mvs Exp $ */
/* /*
* System call numbers. * System call numbers.
* *
* DO NOT EDIT-- this file is automatically generated. * DO NOT EDIT-- this file is automatically generated.
* created from; OpenBSD: syscalls.master,v 1.247 2023/05/04 09:40:36 mvs Exp * created from; OpenBSD: syscalls.master,v 1.248 2023/05/18 10:23:19 mvs Exp
*/ */
/* syscall: "syscall" ret: "int" args: "int" "..." */ /* syscall: "syscall" ret: "int" args: "int" "..." */

View file

@ -1,10 +1,10 @@
/* $OpenBSD: syscallargs.h,v 1.265 2023/05/04 09:41:15 mvs Exp $ */ /* $OpenBSD: syscallargs.h,v 1.266 2023/05/18 10:24:28 mvs Exp $ */
/* /*
* System call argument lists. * System call argument lists.
* *
* DO NOT EDIT-- this file is automatically generated. * DO NOT EDIT-- this file is automatically generated.
* created from; OpenBSD: syscalls.master,v 1.247 2023/05/04 09:40:36 mvs Exp * created from; OpenBSD: syscalls.master,v 1.248 2023/05/18 10:23:19 mvs Exp
*/ */
#ifdef syscallarg #ifdef syscallarg

View file

@ -1,4 +1,4 @@
/* $OpenBSD: sysctl.h,v 1.232 2023/01/07 05:24:58 guenther Exp $ */ /* $OpenBSD: sysctl.h,v 1.233 2023/05/17 22:12:51 kettenis Exp $ */
/* $NetBSD: sysctl.h,v 1.16 1996/04/09 20:55:36 cgd Exp $ */ /* $NetBSD: sysctl.h,v 1.16 1996/04/09 20:55:36 cgd Exp $ */
/* /*
@ -948,7 +948,8 @@ struct kinfo_file {
#define HW_SMT 24 /* int: enable SMT/HT/CMT */ #define HW_SMT 24 /* int: enable SMT/HT/CMT */
#define HW_NCPUONLINE 25 /* int: number of cpus being used */ #define HW_NCPUONLINE 25 /* int: number of cpus being used */
#define HW_POWER 26 /* int: machine has wall-power */ #define HW_POWER 26 /* int: machine has wall-power */
#define HW_MAXID 27 /* number of valid hw ids */ #define HW_BATTERY 27 /* node: battery */
#define HW_MAXID 30 /* number of valid hw ids */
#define CTL_HW_NAMES { \ #define CTL_HW_NAMES { \
{ 0, 0 }, \ { 0, 0 }, \
@ -978,6 +979,22 @@ struct kinfo_file {
{ "smt", CTLTYPE_INT }, \ { "smt", CTLTYPE_INT }, \
{ "ncpuonline", CTLTYPE_INT }, \ { "ncpuonline", CTLTYPE_INT }, \
{ "power", CTLTYPE_INT }, \ { "power", CTLTYPE_INT }, \
{ "battery", CTLTYPE_NODE }, \
}
/*
* HW_BATTERY
*/
#define HW_BATTERY_CHARGEMODE 1 /* int: battery charging mode */
#define HW_BATTERY_CHARGESTART 2 /* int: battery start charge percent */
#define HW_BATTERY_CHARGESTOP 3 /* int: battery stop charge percent */
#define HW_BATTERY_MAXID 4
#define CTL_HW_BATTERY_NAMES { \
{ 0, 0 }, \
{ "chargemode", CTLTYPE_INT }, \
{ "chargestart", CTLTYPE_INT }, \
{ "chargestop", CTLTYPE_INT }, \
} }
/* /*

View file

@ -1,5 +1,5 @@
# ex:ts=8 sw=4: # ex:ts=8 sw=4:
# $OpenBSD: PackingList.pm,v 1.150 2023/05/16 14:31:26 espie Exp $ # $OpenBSD: PackingList.pm,v 1.151 2023/05/17 21:15:03 espie Exp $
# #
# Copyright (c) 2003-2014 Marc Espie <espie@openbsd.org> # Copyright (c) 2003-2014 Marc Espie <espie@openbsd.org>
# #
@ -527,7 +527,7 @@ sub to_cache
{ {
my ($self) = @_; my ($self) = @_;
return if defined $plist_cache->{$self->pkgname}; return if defined $plist_cache->{$self->pkgname};
my $plist = OpenBSD::PackingList::Depend->new; my $plist = OpenBSD::PackingList->new;
for my $c (@cache_categories) { for my $c (@cache_categories) {
if (defined $self->{$c}) { if (defined $self->{$c}) {
$plist->{$c} = $self->{$c}; $plist->{$c} = $self->{$c};

View file

@ -1,4 +1,4 @@
$OpenBSD: style.pod,v 1.1 2020/12/20 15:30:58 daniel Exp $ $OpenBSD: style.pod,v 1.2 2023/05/18 16:30:01 espie Exp $
=head1 NAME =head1 NAME
@ -16,6 +16,9 @@ Just as for L<style(9)>, indentation is an 8 character tab,
and statements continuing on the next line are indented and statements continuing on the next line are indented
by four more spaces. by four more spaces.
Systematically C<use v5.36> or later which yields C<strict>, C<warnings>,
C<say> and function signatures.
=head2 Subroutines and methods =head2 Subroutines and methods
Prefer object-oriented over procedural style for new code. Prefer object-oriented over procedural style for new code.
@ -32,46 +35,78 @@ Name the constructor new() unless there are better options.
Inside methods, call the object C<$self> unless there are reasons not to. Inside methods, call the object C<$self> unless there are reasons not to.
For functions with multiple parameters, Use signatures for every function (except delegations), so that the number
use list assignment to retrieve the arguments: of parameters can be checked.
sub m3 sub m3($self, $p1, $p2)
{ {
my ($self, $p1, $p2) = @_;
... ...
} }
Usually, there is no need to check the number of arguments. Accordingly, avoid calling code refs without parentheses, since this creates
an implicit C<@_> reference.
For functions with exactly one parameter, one can alternatively Note that signatures can also absorb an arbitrary number of parameters with
retrieve the argument with the shift() function: C<@l> and set default parameter values like in C++, e.g.
sub width sub do_backsubst($subst, $string, $unsubst = undef,
{ $context = 'OpenBSD::PackingElement');
my $self = shift;
...
}
Because it takes no argument apart from the object itself, calling For methods that take no argument apart from the object itself, remove
such a method doesn't need trailing empty parentheses: trailing parentheses for the method call:
my $columns = $object->width; my $columns = $object->width;
If a function passes on an arbitrary number of arguments If a function passes on an arbitrary number of arguments
to another function: to another function:
sub wrapper_method sub wrapper_method($self, @p)
{ {
my $self = shift;
... ...
do_something_with(@_); do_something_with(@p);
} }
Mark the last expression at the end of a function with an explicit Anonymous subs should also use signatures
B<return> unless the function is is not intended to return anything.
Avoid using the wantarray() function except as an optimization; $state->{opt}{x} =
it should not change the semantics of the subroutine. sub($opt) {
push ${$state->{xlist}}, $opt);
};
(Exception: signal handlers are currently not specified and may take an
arbitrary number of parameters for C<__DIE__> and C<__WARN__>.
Mark the last expression at the end of a function with an explicit
B<return> unless the function is is not intended to return anything,
or for "constant" methods
sub isFile($)
{
1;
}
Do not name parameters to methods unless actually used.
For documentation, use a comment in that case (especially useful
for base methods)
# $self->foo($state):
# explain what foo does
sub foo($, $)
{
}
Avoid using old-style function prototypes unless absolutely necessary
to create syntax:
sub try :prototype(&@)
{
my ($try, $catch) = @_;
eval { &$try() };
dienow($@, $catch);
}
Only use the wantarray() built-in as an optimization;
it should never change the semantics of the subroutine.
For example, suppose there is a function returning a list, For example, suppose there is a function returning a list,
and while the question whether the list is empty sometimes and while the question whether the list is empty sometimes
needs to be asked, the number of elements never matters. needs to be asked, the number of elements never matters.
@ -102,16 +137,14 @@ simply mark internal methods by prefixing their names with C<_>.
Treat anonymous subroutines just like other code, Treat anonymous subroutines just like other code,
indenting them by one tab: indenting them by one tab:
my $s = sub { my $s = sub($self) {
my $self = shift;
... ...
}; };
When passing an anonymous function as an argument, start it on a new line: When passing an anonymous function as an argument, start it on a new line:
f($a1, $a2, f($a1, $a2,
sub { sub($self) {
my $self = shift;
... ...
}); });
@ -123,7 +156,9 @@ into the same source file is fine.
Avoid multiple inheritance unless absolutely necessary Avoid multiple inheritance unless absolutely necessary
because it almost always turns into a mess. because it almost always turns into a mess.
Including some behavior from a different class (mixin) Including some behavior from a different class (mixin)
is best done on a per-method basis. is best done on a per-method basis, but explicitly annotate the mixins
as such.
Delegating from one method of one class to a method of another class, Delegating from one method of one class to a method of another class,
passing C<@_> completely unchanged, can be done with the following syntax: passing C<@_> completely unchanged, can be done with the following syntax:
@ -134,6 +169,9 @@ passing C<@_> completely unchanged, can be done with the following syntax:
&Lender::visit_notary; # no parentheses here &Lender::visit_notary; # no parentheses here
} }
This is the only case where a code ref should be called without explicit
parameters, and where a method can be declared without a prototype.
If a program often uses fork(), set If a program often uses fork(), set
$DB::inhibit_exit = 0; $DB::inhibit_exit = 0;