mirror of https://github.com/red-prig/fpPS4.git
This commit is contained in:
parent
071795ea0d
commit
b6926ffff1
|
@ -0,0 +1,82 @@
|
|||
unit dev_dmem;
|
||||
|
||||
{$mode ObjFPC}{$H+}
|
||||
{$CALLING SysV_ABI_CDecl}
|
||||
|
||||
interface
|
||||
|
||||
uses
|
||||
kern_conf;
|
||||
|
||||
procedure dmemdev_init();
|
||||
|
||||
implementation
|
||||
|
||||
uses
|
||||
errno,
|
||||
vuio,
|
||||
subr_uio,
|
||||
vm,
|
||||
kern_dmem;
|
||||
|
||||
Const
|
||||
SCE_KERNEL_MAIN_DMEM_SIZE=$180000000; //6GB
|
||||
|
||||
Function dmem_ioctl(dev:p_cdev;cmd:QWORD;data:Pointer;fflag:Integer):Integer;
|
||||
begin
|
||||
Result:=0;
|
||||
|
||||
Writeln('dmem_ioctl("',dev^.si_name,'",0x',HexStr(cmd,8),',0x',HexStr(fflag,8),')');
|
||||
|
||||
case cmd of
|
||||
$4008800A: //sceKernelGetDirectMemorySize
|
||||
begin
|
||||
PQWORD(data)^:=SCE_KERNEL_MAIN_DMEM_SIZE;
|
||||
end;
|
||||
else
|
||||
Assert(False);
|
||||
end;
|
||||
|
||||
end;
|
||||
|
||||
Function dmem_mmap(dev:p_cdev;offset:vm_ooffset_t;paddr:p_vm_paddr_t;nprot:Integer;memattr:p_vm_memattr_t):Integer;
|
||||
begin
|
||||
Result:=0;
|
||||
|
||||
Writeln('dmem_mmap("',dev^.si_name,'",0x',HexStr(offset,8),',0x',HexStr(paddr),',',nprot,')');
|
||||
Assert(False);
|
||||
end;
|
||||
|
||||
const
|
||||
dmem_cdevsw:t_cdevsw=(
|
||||
d_version :D_VERSION;
|
||||
d_flags :0;
|
||||
d_name :'dmem';
|
||||
d_open :nil;
|
||||
d_fdopen :nil;
|
||||
d_close :nil;
|
||||
d_read :nil;
|
||||
d_write :nil;
|
||||
d_ioctl :@dmem_ioctl;
|
||||
d_poll :nil;
|
||||
d_mmap :@dmem_mmap;
|
||||
d_strategy :nil;
|
||||
d_dump :nil;
|
||||
d_kqfilter :nil;
|
||||
d_purge :nil;
|
||||
d_mmap_single:nil;
|
||||
);
|
||||
|
||||
procedure dmemdev_init();
|
||||
var
|
||||
i:Integer;
|
||||
begin
|
||||
For i:=0 to 2 do
|
||||
begin
|
||||
make_dev(@dmem_cdevsw,i,0,0,&777,'dmem%d',[i]);
|
||||
end;
|
||||
end;
|
||||
|
||||
|
||||
end.
|
||||
|
|
@ -13,9 +13,9 @@ const
|
|||
|
||||
var
|
||||
zero_region:Pointer;
|
||||
_zero_region:array[0..ZERO_REGION_SIZE-1] of Byte;
|
||||
|
||||
procedure init_zero_region;
|
||||
procedure free_zero_region;
|
||||
|
||||
Function null_modevent(_mod,_type:Integer):Integer; //DEV_MODULE(nil, null_modevent, nil);
|
||||
|
||||
|
@ -109,7 +109,9 @@ begin
|
|||
end;
|
||||
end;
|
||||
else
|
||||
begin
|
||||
error:=ENOIOCTL;
|
||||
end;
|
||||
end;
|
||||
|
||||
Exit(error);
|
||||
|
@ -132,21 +134,36 @@ begin
|
|||
end;
|
||||
end;
|
||||
else
|
||||
begin
|
||||
error:=ENOIOCTL;
|
||||
end;
|
||||
end;
|
||||
|
||||
Exit(error);
|
||||
end;
|
||||
|
||||
procedure init_zero_region;
|
||||
var
|
||||
buf:Pointer;
|
||||
begin
|
||||
if (zero_region=nil) then
|
||||
begin
|
||||
FillChar(_zero_region,SizeOf(_zero_region),0);
|
||||
zero_region:=@_zero_region;
|
||||
buf:=AllocMem(ZERO_REGION_SIZE);
|
||||
if (System.InterlockedCompareExchange(zero_region,buf,nil)<>nil) then
|
||||
begin
|
||||
FreeMem(buf);
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
|
||||
procedure free_zero_region;
|
||||
var
|
||||
buf:Pointer;
|
||||
begin
|
||||
buf:=System.InterlockedExchange(zero_region,nil);
|
||||
FreeMem(buf);
|
||||
end;
|
||||
|
||||
{ ARGSUSED }
|
||||
Function zero_read(dev:p_cdev;uio:p_uio;ioflag:Integer):Integer;
|
||||
var
|
||||
|
@ -188,6 +205,7 @@ begin
|
|||
begin
|
||||
destroy_dev(null_dev);
|
||||
destroy_dev(zero_dev);
|
||||
free_zero_region;
|
||||
end;
|
||||
|
||||
MOD_SHUTDOWN:;
|
||||
|
|
|
@ -33,7 +33,7 @@ var
|
|||
}
|
||||
Function ttydev_open(dev:p_cdev;oflags,devtype:Integer):Integer;
|
||||
begin
|
||||
Writeln('ttydev_open(',dev^.si_name,',',oflags,',',devtype,')');
|
||||
Writeln('ttydev_open("',dev^.si_name,'",',oflags,',',devtype,')');
|
||||
Result:=0;
|
||||
end;
|
||||
|
||||
|
@ -110,7 +110,7 @@ begin
|
|||
else;
|
||||
end;
|
||||
|
||||
Writeln('ttydev_ioctl(0',dev^.si_name,',0x',HexStr(cmd,8),',0x',HexStr(data),',0x',HexStr(fflag,8));
|
||||
Writeln('ttydev_ioctl("',dev^.si_name,'",0x',HexStr(cmd,8),',0x',HexStr(data),',0x',HexStr(fflag,8),')');
|
||||
//error:=tty_ioctl(tp, cmd, data, fflag, td);
|
||||
|
||||
//done:
|
||||
|
@ -343,27 +343,27 @@ const
|
|||
* will be logged in the kernel message buffer.
|
||||
}
|
||||
|
||||
function tty_makedev(fmt:PChar;const Args:Array of const):p_cdev; register;
|
||||
var
|
||||
dev:p_cdev;
|
||||
uid:uid_t;
|
||||
gid:gid_t;
|
||||
mode:mode_t;
|
||||
begin
|
||||
// User device.
|
||||
uid :=0;
|
||||
gid :=GID_TTY;
|
||||
mode:=S_IRUSR or S_IWUSR or S_IWGRP;
|
||||
function tty_makedev(fmt:PChar;const Args:Array of const):p_cdev; register;
|
||||
var
|
||||
dev:p_cdev;
|
||||
uid:uid_t;
|
||||
gid:gid_t;
|
||||
mode:mode_t;
|
||||
begin
|
||||
// User device.
|
||||
uid :=0;
|
||||
gid :=GID_TTY;
|
||||
mode:=S_IRUSR or S_IWUSR or S_IWGRP;
|
||||
|
||||
dev:=make_dev_cred(@ttydev_cdevsw, 0, uid, gid, mode, fmt, Args);
|
||||
dev:=make_dev_cred(@ttydev_cdevsw, 0, uid, gid, mode, fmt, Args);
|
||||
|
||||
Result:=dev;
|
||||
end;
|
||||
Result:=dev;
|
||||
end;
|
||||
|
||||
procedure ttyconsdev_init();
|
||||
begin
|
||||
dev_console:=make_dev_credf(MAKEDEV_ETERNAL, @ttyconsdev_cdevsw, 0, UID_ROOT, GID_WHEEL, &600, 'console',[]);
|
||||
|
||||
//
|
||||
tty_makedev('deci_stderr',[]);
|
||||
tty_makedev('deci_stdin' ,[]);
|
||||
tty_makedev('deci_stdout',[]);
|
||||
|
|
|
@ -227,7 +227,9 @@ begin
|
|||
if (devp^<>fp^.f_data) then
|
||||
begin
|
||||
if (dswp^<>nil) then
|
||||
begin
|
||||
dev_relthread(devp^, ref^);
|
||||
end;
|
||||
|
||||
Exit(ENXIO);
|
||||
end;
|
||||
|
@ -252,7 +254,9 @@ begin
|
|||
error:=0;
|
||||
datap^:=p^.cdpd_data;
|
||||
end else
|
||||
begin
|
||||
error:=ENOENT;
|
||||
end;
|
||||
|
||||
Exit(error);
|
||||
end;
|
||||
|
@ -390,7 +394,9 @@ begin
|
|||
|
||||
error:=devfs_populate_vp(vp);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
|
||||
i:=buflen^;
|
||||
dd:=vp^.v_data;
|
||||
|
@ -500,7 +506,9 @@ var
|
|||
begin
|
||||
not_found:=0;
|
||||
if ((de^.de_flags and DE_DOOMED)<>0) then
|
||||
begin
|
||||
not_found:=1;
|
||||
end;
|
||||
if DEVFS_DE_DROP(de) then
|
||||
begin
|
||||
Assert(not_found=1,'DEVFS de dropped but not doomed');
|
||||
|
@ -632,7 +640,9 @@ loop:
|
|||
VI_UNLOCK(vp);
|
||||
|
||||
if ((dev^.si_flags and SI_ETERNAL)<>0) then
|
||||
begin
|
||||
vp^.v_vflag:=vp^.v_vflag or VV_ETERNALDEV;
|
||||
end;
|
||||
|
||||
vp^.v_op:=@devfs_specops;
|
||||
end else
|
||||
|
@ -689,16 +699,22 @@ begin
|
|||
|
||||
de:=vp^.v_data;
|
||||
if (vp^.v_type=VDIR) then
|
||||
begin
|
||||
de:=de^.de_dir;
|
||||
end;
|
||||
|
||||
error:=vaccess(vp^.v_type, de^.de_mode, de^.de_uid, de^.de_gid, ap^.a_accmode, nil);
|
||||
if (error=0) then
|
||||
begin
|
||||
Exit(0);
|
||||
end;
|
||||
if (error<>EACCES) then
|
||||
Exit(error);
|
||||
{ We do, however, allow access to the controlling terminal }
|
||||
if ((p_proc.p_flag and P_CONTROLT)=0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
//if (ap^.a_td^.td_proc^.p_session^.s_ttydp=de^.de_cdp) then
|
||||
// Exit(0);
|
||||
Exit(error);
|
||||
|
@ -721,7 +737,9 @@ begin
|
|||
* XXX: insmntque1() failure.
|
||||
}
|
||||
if (vp^.v_data=nil) then
|
||||
begin
|
||||
Exit(0);
|
||||
end;
|
||||
|
||||
{
|
||||
* Hack: a tty device that is a controlling terminal
|
||||
|
@ -750,7 +768,9 @@ begin
|
|||
//end;
|
||||
//sx_xunlock(@proctree_lock);
|
||||
if (oldvp<>nil) then
|
||||
begin
|
||||
vrele(oldvp);
|
||||
end;
|
||||
{
|
||||
* We do not want to really close the device if it
|
||||
* is still in use unless we are trying to close it
|
||||
|
@ -865,7 +885,9 @@ begin
|
|||
|
||||
error:=devfs_populate_vp(vp);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
|
||||
dmp:=VFSTODEVFS(vp^.v_mount);
|
||||
sx_xunlock(@dmp^.dm_lock);
|
||||
|
@ -958,10 +980,12 @@ begin
|
|||
fgn:=data;
|
||||
p:=devtoname(dev);
|
||||
i:=strlen(p) + 1;
|
||||
|
||||
if (i > fgn^.len) then
|
||||
error:=EINVAL
|
||||
else
|
||||
error:=copyout(p, fgn^.buf, i);
|
||||
|
||||
td^.td_fpop:=fpop;
|
||||
dev_relthread(dev, ref);
|
||||
Exit(error);
|
||||
|
@ -970,7 +994,9 @@ begin
|
|||
td^.td_fpop:=nil;
|
||||
dev_relthread(dev, ref);
|
||||
if (error=ENOIOCTL) then
|
||||
begin
|
||||
error:=ENOTTY;
|
||||
end;
|
||||
if (error=0) and (com=TIOCSCTTY) then
|
||||
begin
|
||||
vp:=fp^.f_vnode;
|
||||
|
@ -995,7 +1021,9 @@ begin
|
|||
|
||||
{ Get rid of reference to old control tty }
|
||||
if (vpold<>nil) then
|
||||
begin
|
||||
vrele(vpold);
|
||||
end;
|
||||
end;
|
||||
Exit(error);
|
||||
end;
|
||||
|
@ -1032,10 +1060,14 @@ begin
|
|||
error:=0;
|
||||
//error:=prison_check(td^.td_ucred, dcr);
|
||||
if (error=0) then
|
||||
begin
|
||||
Exit(0);
|
||||
end;
|
||||
{ We do, however, allow access to the controlling terminal }
|
||||
if ((p_proc.p_flag and P_CONTROLT)=0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
//if (td^.td_proc^.p_session^.s_ttydp=cdp) then
|
||||
// Exit(0);
|
||||
Exit(error);
|
||||
|
@ -1067,22 +1099,32 @@ begin
|
|||
vpp^:=nil;
|
||||
|
||||
if ((flags and ISLASTCN)<>0) and (nameiop=RENAME) then
|
||||
begin
|
||||
Exit(EOPNOTSUPP);
|
||||
end;
|
||||
|
||||
if (dvp^.v_type<>VDIR) then
|
||||
begin
|
||||
Exit(ENOTDIR);
|
||||
end;
|
||||
|
||||
if (((flags and ISDOTDOT)<>0) and ((dvp^.v_vflag and VV_ROOT)<>0)) then
|
||||
begin
|
||||
Exit(EIO);
|
||||
end;
|
||||
|
||||
error:=VOP_ACCESS(dvp, VEXEC);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
|
||||
if (cnp^.cn_namelen=1) and (pname^='.') then
|
||||
begin
|
||||
if ((flags and ISLASTCN) and nameiop<>LOOKUP) then
|
||||
begin
|
||||
Exit(EINVAL);
|
||||
end;
|
||||
vpp^:=dvp;
|
||||
VREF(dvp);
|
||||
Exit(0);
|
||||
|
@ -1091,7 +1133,9 @@ begin
|
|||
if ((flags and ISDOTDOT)<>0) then
|
||||
begin
|
||||
if ((flags and ISLASTCN)<>0) and (nameiop<>LOOKUP) then
|
||||
begin
|
||||
Exit(EINVAL);
|
||||
end;
|
||||
de:=devfs_parent_dirent(dd);
|
||||
if (de=nil) then Exit(ENOENT);
|
||||
|
||||
|
@ -1152,7 +1196,9 @@ begin
|
|||
devfs_unmount_final(dmp);
|
||||
|
||||
if (cdev<>nil) then
|
||||
begin
|
||||
dev_rel(cdev);
|
||||
end;
|
||||
|
||||
Exit(ENOENT);
|
||||
end;
|
||||
|
@ -1190,13 +1236,17 @@ begin
|
|||
end;
|
||||
|
||||
if (devfs_prison_check(de)<>0) then
|
||||
begin
|
||||
Exit(ENOENT);
|
||||
end;
|
||||
|
||||
if (cnp^.cn_nameiop=DELETE) and ((flags and ISLASTCN)<>0) then
|
||||
begin
|
||||
error:=VOP_ACCESS(dvp, VWRITE);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
if (vpp^=dvp) then
|
||||
begin
|
||||
VREF(dvp);
|
||||
|
@ -1428,7 +1478,9 @@ var
|
|||
fpop:p_file;
|
||||
begin
|
||||
if (uio^.uio_resid > DEVFS_IOSIZE_MAX) then
|
||||
begin
|
||||
Exit(EINVAL);
|
||||
end;
|
||||
|
||||
td:=curkthread;
|
||||
fpop:=td^.td_fpop;
|
||||
|
@ -1444,7 +1496,9 @@ begin
|
|||
foffset_lock_uio(fp, uio, flags or FOF_NOLOCK);
|
||||
error:=dsw^.d_read(dev, uio, ioflag);
|
||||
if (uio^.uio_resid<>resid) or ((error=0) and (resid<>0)) then
|
||||
begin
|
||||
vfs_timestamp(@dev^.si_atime);
|
||||
end;
|
||||
td^.td_fpop:=fpop;
|
||||
dev_relthread(dev, ref);
|
||||
|
||||
|
@ -1466,11 +1520,15 @@ begin
|
|||
tmp_ncookies:=nil;
|
||||
|
||||
if (ap^.a_vp^.v_type<>VDIR) then
|
||||
begin
|
||||
Exit(ENOTDIR);
|
||||
end;
|
||||
|
||||
uio:=ap^.a_uio;
|
||||
if (uio^.uio_offset < 0) then
|
||||
begin
|
||||
Exit(EINVAL);
|
||||
end;
|
||||
|
||||
{
|
||||
* XXX: This is a temporary hack to get around this filesystem not
|
||||
|
@ -1616,18 +1674,24 @@ begin
|
|||
begin
|
||||
de_cov:=devfs_find(dd, de^.de_dirent^.d_name, de^.de_dirent^.d_namlen, 0);
|
||||
if (de_cov<>nil) then
|
||||
begin
|
||||
de_cov^.de_flags:=de_cov^.de_flags and (not DE_COVERED);
|
||||
end;
|
||||
end;
|
||||
|
||||
{ We need to unlock dvp because devfs_delete() may lock it. }
|
||||
VOP_UNLOCK(vp, 0);
|
||||
if (dvp<>vp) then
|
||||
begin
|
||||
VOP_UNLOCK(dvp, 0);
|
||||
end;
|
||||
|
||||
devfs_delete(dmp, de, 0);
|
||||
sx_xunlock(@dmp^.dm_lock);
|
||||
if (dvp<>vp) then
|
||||
begin
|
||||
vn_lock(dvp, LK_EXCLUSIVE or LK_RETRY);
|
||||
end;
|
||||
|
||||
vn_lock(vp, LK_EXCLUSIVE or LK_RETRY);
|
||||
end else
|
||||
|
@ -1712,7 +1776,9 @@ begin
|
|||
dev_unlock();
|
||||
dev_rel(@cdp^.cdp_c);
|
||||
end else
|
||||
begin
|
||||
dev_unlock();
|
||||
end;
|
||||
|
||||
vn_lock(vp, LK_EXCLUSIVE or LK_RETRY);
|
||||
Exit(0);
|
||||
|
@ -1781,7 +1847,9 @@ begin
|
|||
|
||||
de:=vp^.v_data;
|
||||
if (vp^.v_type=VDIR) then
|
||||
begin
|
||||
de:=de^.de_dir;
|
||||
end;
|
||||
|
||||
error:=0;
|
||||
c:=0;
|
||||
|
@ -1874,12 +1942,16 @@ begin
|
|||
error:=0;
|
||||
//error:=priv_check(curkthread, PRIV_DEVFS_SYMLINK);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
|
||||
dmp:=VFSTODEVFS(ap^.a_dvp^.v_mount);
|
||||
|
||||
if (devfs_populate_vp(ap^.a_dvp)<>0) then
|
||||
begin
|
||||
Exit(ENOENT);
|
||||
end;
|
||||
|
||||
dd:=ap^.a_dvp^.v_data;
|
||||
de_cov:=devfs_find(dd, ap^.a_cnp^.cn_nameptr, ap^.a_cnp^.cn_namelen, 0);
|
||||
|
@ -1937,7 +2009,9 @@ begin
|
|||
td:=curkthread;
|
||||
|
||||
if (uio^.uio_resid > DEVFS_IOSIZE_MAX) then
|
||||
begin
|
||||
Exit(EINVAL);
|
||||
end;
|
||||
|
||||
fpop:=td^.td_fpop;
|
||||
error:=devfs_fp_check(fp, @dev, @dsw, @ref);
|
||||
|
@ -1947,7 +2021,9 @@ begin
|
|||
ioflag:=fp^.f_flag and (O_NONBLOCK or O_DIRECT or O_FSYNC);
|
||||
|
||||
if ((ioflag and O_DIRECT)<>0) then
|
||||
begin
|
||||
ioflag:=ioflag or IO_DIRECT;
|
||||
end;
|
||||
|
||||
foffset_lock_uio(fp, uio, flags or FOF_NOLOCK);
|
||||
|
||||
|
|
|
@ -0,0 +1,40 @@
|
|||
unit kern_dmem;
|
||||
|
||||
{$mode ObjFPC}{$H+}
|
||||
{$CALLING SysV_ABI_CDecl}
|
||||
|
||||
interface
|
||||
|
||||
function sys_dmem_container(d_pool_id:Integer):Integer;
|
||||
|
||||
implementation
|
||||
|
||||
uses
|
||||
errno,
|
||||
kern_thr;
|
||||
|
||||
const
|
||||
default_pool_id=1;
|
||||
|
||||
function sys_dmem_container(d_pool_id:Integer):Integer;
|
||||
var
|
||||
td:p_kthread;
|
||||
begin
|
||||
td:=curkthread;
|
||||
if (td=nil) then Exit(-1);
|
||||
|
||||
td^.td_retval[0]:=default_pool_id;
|
||||
Result:=0;
|
||||
|
||||
if (d_pool_id<>-1) then
|
||||
begin
|
||||
//Result:=priv_check(td,0x2ad);
|
||||
//(param < 3)
|
||||
Exit(EPERM);
|
||||
end;
|
||||
end;
|
||||
|
||||
|
||||
|
||||
end.
|
||||
|
|
@ -56,7 +56,8 @@ uses
|
|||
kern_event,
|
||||
machdep,
|
||||
kern_dlsym,
|
||||
kern_authinfo;
|
||||
kern_authinfo,
|
||||
vfs_syscalls;
|
||||
|
||||
function exec_alloc_args(args:p_image_args):Integer;
|
||||
begin
|
||||
|
@ -1197,6 +1198,13 @@ begin
|
|||
Exit(0);
|
||||
end;
|
||||
|
||||
procedure init_tty;
|
||||
begin
|
||||
kern_openat(STDIN_FILENO ,'/dev/deci_stdin' ,UIO_SYSSPACE,O_RDWR,0);
|
||||
kern_openat(STDOUT_FILENO,'/dev/deci_stdout',UIO_SYSSPACE,O_RDWR,0);
|
||||
kern_openat(STDERR_FILENO,'/dev/deci_stderr',UIO_SYSSPACE,O_RDWR,0);
|
||||
end;
|
||||
|
||||
const
|
||||
fexecv_proc_title='(fexecv)';
|
||||
|
||||
|
@ -1422,6 +1430,9 @@ begin
|
|||
//copy authinfo
|
||||
g_authinfo:=imgp^.authinfo;
|
||||
|
||||
//init std tty
|
||||
init_tty;
|
||||
|
||||
{
|
||||
* Free any resources malloc'd earlier that we didn't use.
|
||||
}
|
||||
|
|
|
@ -414,6 +414,12 @@ begin
|
|||
|
||||
if (pid<>g_pid) then Exit(EINVAL);
|
||||
|
||||
//G_APPINFO.mmap_flags:=G_APPINFO.mmap_flags or 1;
|
||||
if (p_proc.p_sce_replay_exec<>0) then
|
||||
begin
|
||||
G_APPINFO.mmap_flags:=G_APPINFO.mmap_flags or 2;
|
||||
end;
|
||||
|
||||
//sceSblACMgrIsSystemUcred()!=0 -> any proc
|
||||
//sceSblACMgrIsSystemUcred()==0 -> cur proc
|
||||
|
||||
|
@ -425,6 +431,10 @@ begin
|
|||
if (Result=0) then
|
||||
begin
|
||||
G_APPINFO:=APPINFO;
|
||||
if (p_proc.p_sce_replay_exec<>0) then
|
||||
begin
|
||||
G_APPINFO.mmap_flags:=G_APPINFO.mmap_flags or 2;
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
|
||||
|
|
|
@ -544,12 +544,16 @@ end;
|
|||
|
||||
|
||||
procedure PROC_INIT;
|
||||
const
|
||||
osreldate=$000DBBA0;
|
||||
begin
|
||||
FillChar(p_proc,SizeOf(p_proc),0);
|
||||
mtx_init(p_proc.p_mtx,'process lock');
|
||||
|
||||
knlist_init_mtx(@p_proc.p_klist,@p_proc.p_mtx);
|
||||
|
||||
p_proc.p_osrel:=osreldate;
|
||||
|
||||
p_proc.p_randomized_path:='system';
|
||||
|
||||
p_proc.p_ptc:=rdtsc;
|
||||
|
|
|
@ -40,7 +40,8 @@ uses
|
|||
vfs_mountroot,
|
||||
kern_conf,
|
||||
dev_null,
|
||||
dev_tty;
|
||||
dev_tty,
|
||||
dev_dmem;
|
||||
|
||||
var
|
||||
daemon_thr:p_kthread;
|
||||
|
@ -74,6 +75,7 @@ begin
|
|||
//
|
||||
null_modevent(0,MOD_LOAD);
|
||||
ttyconsdev_init();
|
||||
dmemdev_init();
|
||||
end;
|
||||
|
||||
//Manual order of lazy initialization
|
||||
|
|
|
@ -205,6 +205,7 @@ function budget_delete(key:Integer):Integer;
|
|||
function budget_get(key:Integer;ptr:Pointer;psize:PInteger):Integer;
|
||||
function budget_set(key:Integer):Integer;
|
||||
function is_in_sandbox():Integer;
|
||||
function dmem_container(d_pool_id:Integer):Integer;
|
||||
function get_authinfo(pid:Integer;info:Pointer):Integer;
|
||||
function mname(addr:Pointer;len:QWORD;name:PChar):Integer;
|
||||
function dynlib_dlsym(handle:Integer;symbol:pchar;addrp:ppointer):Integer;
|
||||
|
@ -1632,6 +1633,13 @@ asm
|
|||
jmp cerror
|
||||
end;
|
||||
|
||||
function dmem_container(d_pool_id:Integer):Integer; assembler; nostackframe;
|
||||
asm
|
||||
movq $586,%rax
|
||||
call fast_syscall
|
||||
jmp cerror
|
||||
end;
|
||||
|
||||
function get_authinfo(pid:Integer;info:Pointer):Integer; assembler; nostackframe;
|
||||
asm
|
||||
movq $587,%rax
|
||||
|
|
|
@ -13,6 +13,7 @@ uses
|
|||
kern_evf,
|
||||
kern_gpo,
|
||||
kern_sig,
|
||||
kern_dmem,
|
||||
kern_exec,
|
||||
kern_exit,
|
||||
kern_osem,
|
||||
|
@ -2986,7 +2987,7 @@ const
|
|||
),
|
||||
(//[586]
|
||||
sy_narg:1;
|
||||
sy_call:nil;
|
||||
sy_call:@sys_dmem_container;
|
||||
sy_name:'sys_dmem_container'
|
||||
),
|
||||
(//[587]
|
||||
|
|
|
@ -633,6 +633,14 @@
|
|||
<Filename Value="..\dev\dev_tty.pas"/>
|
||||
<IsPartOfProject Value="True"/>
|
||||
</Unit>
|
||||
<Unit>
|
||||
<Filename Value="..\kern\kern_dmem.pas"/>
|
||||
<IsPartOfProject Value="True"/>
|
||||
</Unit>
|
||||
<Unit>
|
||||
<Filename Value="..\dev\dev_dmem.pas"/>
|
||||
<IsPartOfProject Value="True"/>
|
||||
</Unit>
|
||||
</Units>
|
||||
</ProjectOptions>
|
||||
<CompilerOptions>
|
||||
|
|
|
@ -95,7 +95,8 @@ uses
|
|||
kern_sysctl,
|
||||
kern_budget,
|
||||
kern_regmgr,
|
||||
kern_authinfo;
|
||||
kern_authinfo,
|
||||
kern_dmem;
|
||||
|
||||
const
|
||||
PAGE_MAP_COUNT=(qword(VM_MAXUSER_ADDRESS) shr PAGE_SHIFT);
|
||||
|
|
|
@ -105,6 +105,10 @@ const
|
|||
DFLAG_PASSABLE=$01; { may be passed via unix sockets. }
|
||||
DFLAG_SEEKABLE=$02; { seekable / nonsequential }
|
||||
|
||||
STDIN_FILENO =0; // standard input file descriptor
|
||||
STDOUT_FILENO=1; // standard output file descriptor
|
||||
STDERR_FILENO=2; // standard error file descriptor
|
||||
|
||||
type
|
||||
mode_t=Integer;
|
||||
uid_t =Integer;
|
||||
|
|
|
@ -126,7 +126,9 @@ var
|
|||
begin
|
||||
error:=fget_read(fd, CAP_READ or CAP_SEEK, @fp);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
error:=dofileread(fd, fp, auio, -1, 0);
|
||||
fdrop(fp);
|
||||
Exit(error);
|
||||
|
@ -139,7 +141,9 @@ var
|
|||
begin
|
||||
error:=fget_read(fd, CAP_READ, @fp);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
if ((fp^.f_ops^.fo_flags and DFLAG_SEEKABLE)=0) then
|
||||
error:=ESPIPE
|
||||
else
|
||||
|
@ -147,6 +151,7 @@ begin
|
|||
error:=EINVAL
|
||||
else
|
||||
error:=dofileread(fd, fp, auio, offset, FOF_OFFSET);
|
||||
|
||||
fdrop(fp);
|
||||
Exit(error);
|
||||
end;
|
||||
|
@ -158,7 +163,9 @@ var
|
|||
begin
|
||||
error:=fget_write(fd, CAP_WRITE or CAP_SEEK, @fp);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
error:=dofilewrite(fd, fp, auio, -1, 0);
|
||||
fdrop(fp);
|
||||
Exit(error);
|
||||
|
@ -171,7 +178,9 @@ var
|
|||
begin
|
||||
error:=fget_write(fd, CAP_WRITE, @fp);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
if ((fp^.f_ops^.fo_flags and DFLAG_SEEKABLE)=0) then
|
||||
error:=ESPIPE
|
||||
else
|
||||
|
@ -179,6 +188,7 @@ begin
|
|||
error:=EINVAL
|
||||
else
|
||||
error:=dofilewrite(fd, fp, auio, offset, FOF_OFFSET);
|
||||
|
||||
fdrop(fp);
|
||||
Exit(error);
|
||||
end;
|
||||
|
@ -234,7 +244,9 @@ var
|
|||
begin
|
||||
error:=copyinuio(iovp, iovcnt, @auio);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
error:=kern_readv(fd, auio);
|
||||
FreeMem(auio);
|
||||
Exit(error);
|
||||
|
@ -250,7 +262,9 @@ var
|
|||
begin
|
||||
error:=copyinuio(iovp, iovcnt, @auio);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
error:=kern_preadv(fd, auio, offset);
|
||||
FreeMem(auio);
|
||||
Exit(error);
|
||||
|
@ -282,7 +296,9 @@ begin
|
|||
if (error<>0) then
|
||||
begin
|
||||
if (auio^.uio_resid<>cnt) and ((error=ERESTART) or (error=EINTR) or (error=EWOULDBLOCK)) then
|
||||
begin
|
||||
error:=0;
|
||||
end;
|
||||
end;
|
||||
Dec(cnt,auio^.uio_resid);
|
||||
|
||||
|
@ -339,7 +355,9 @@ var
|
|||
begin
|
||||
error:=copyinuio(iovp, iovcnt, @auio);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
error:=kern_writev(fd, auio);
|
||||
FreeMem(auio);
|
||||
Exit(error);
|
||||
|
@ -355,7 +373,9 @@ var
|
|||
begin
|
||||
error:=copyinuio(iovp, iovcnt, @auio);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
error:=kern_pwritev(fd, auio, offset);
|
||||
FreeMem(auio);
|
||||
Exit(error);
|
||||
|
@ -385,7 +405,9 @@ begin
|
|||
if (error<>0) then
|
||||
begin
|
||||
if (auio^.uio_resid<>cnt) and ((error=ERESTART) or (error=EINTR) or (error=EWOULDBLOCK)) then
|
||||
begin
|
||||
error:=0;
|
||||
end;
|
||||
{ Socket layer is responsible for issuing SIGPIPE. }
|
||||
if (fp^.f_type<>DTYPE_SOCKET) and (error=EPIPE) then
|
||||
begin
|
||||
|
@ -412,10 +434,14 @@ var
|
|||
error:Integer;
|
||||
begin
|
||||
if (length < 0) then
|
||||
begin
|
||||
Exit(EINVAL);
|
||||
end;
|
||||
error:=fget(fd, CAP_FTRUNCATE, @fp);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
if ((fp^.f_flag and FWRITE)=0) then
|
||||
begin
|
||||
fdrop(fp);
|
||||
|
@ -441,7 +467,9 @@ var
|
|||
begin
|
||||
error:=fget(fd, CAP_IOCTL, @fp);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
if ((fp^.f_flag and (FREAD or FWRITE))=0) then
|
||||
begin
|
||||
fdrop(fp);
|
||||
|
@ -461,19 +489,23 @@ begin
|
|||
FIONBIO:
|
||||
begin
|
||||
tmp:=PInteger(data)^;
|
||||
|
||||
if (tmp<>0) then
|
||||
atomic_set_int(@fp^.f_flag, FNONBLOCK)
|
||||
else
|
||||
atomic_clear_int(@fp^.f_flag, FNONBLOCK);
|
||||
|
||||
data:=@tmp;
|
||||
end;
|
||||
FIOASYNC:
|
||||
begin
|
||||
tmp:=PInteger(data)^;
|
||||
|
||||
if (tmp<>0) then
|
||||
atomic_set_int(@fp^.f_flag, FASYNC)
|
||||
else
|
||||
atomic_clear_int(@fp^.f_flag, FASYNC);
|
||||
|
||||
data:=@tmp;
|
||||
end;
|
||||
end;
|
||||
|
@ -490,6 +522,7 @@ var
|
|||
smalldata:array[0..SYS_IOCTL_SMALL_SIZE-1] of Byte; //__aligned(SYS_IOCTL_SMALL_ALIGN)
|
||||
arg,error:Integer;
|
||||
size:DWORD;
|
||||
kern_data:Pointer;
|
||||
begin
|
||||
if (com > $ffffffff) then
|
||||
begin
|
||||
|
@ -506,7 +539,9 @@ begin
|
|||
((com and (IOC_VOID or IOC_IN or IOC_OUT))=0) or
|
||||
(((com and (IOC_IN or IOC_OUT))<>0) and (size=0)) or
|
||||
(((com and IOC_VOID)<>0) and (size > 0) and (size<>sizeof(Integer))) then
|
||||
begin
|
||||
Exit(ENOTTY);
|
||||
end;
|
||||
|
||||
if (size > 0) then
|
||||
begin
|
||||
|
@ -514,22 +549,26 @@ begin
|
|||
begin
|
||||
{ Integer argument. }
|
||||
arg:=ptrint(data);
|
||||
data:=@arg;
|
||||
kern_data:=@arg;
|
||||
size:=0;
|
||||
end else
|
||||
begin
|
||||
if (size > SYS_IOCTL_SMALL_SIZE) then
|
||||
data:=AllocMem(size)
|
||||
kern_data:=AllocMem(size)
|
||||
else
|
||||
data:=@smalldata;
|
||||
kern_data:=@smalldata;
|
||||
end;
|
||||
end else
|
||||
data:=@data;
|
||||
begin
|
||||
kern_data:=@curkthread^.td_frame.tf_rsi;
|
||||
end;
|
||||
if ((com and IOC_IN)<>0) then
|
||||
begin
|
||||
error:=copyin(data, data, size);
|
||||
error:=copyin(data, kern_data, size);
|
||||
if (error<>0) then
|
||||
begin
|
||||
goto _out;
|
||||
end;
|
||||
end else
|
||||
if ((com and IOC_OUT)<>0) then
|
||||
begin
|
||||
|
@ -537,17 +576,21 @@ begin
|
|||
* Zero the buffer so the user always
|
||||
* gets back something deterministic.
|
||||
}
|
||||
FillChar(data,size,0);
|
||||
FillChar(kern_data^,size,0);
|
||||
end;
|
||||
|
||||
error:=kern_ioctl(fd, com, data);
|
||||
error:=kern_ioctl(fd, com, kern_data);
|
||||
|
||||
if (error=0) and ((com and IOC_OUT)<>0) then
|
||||
error:=copyout(data, data, size);
|
||||
begin
|
||||
error:=copyout(kern_data, data, size);
|
||||
end;
|
||||
|
||||
_out:
|
||||
if (size > SYS_IOCTL_SMALL_SIZE) then
|
||||
FreeMem(data);
|
||||
begin
|
||||
FreeMem(kern_data);
|
||||
end;
|
||||
Exit(error);
|
||||
end;
|
||||
|
||||
|
@ -561,7 +604,9 @@ begin
|
|||
* of specific filesystem implementations.
|
||||
}
|
||||
if (events and (not POLLSTANDARD))<>0 then
|
||||
begin
|
||||
Exit(POLLNVAL);
|
||||
end;
|
||||
|
||||
Exit(events and (POLLIN or POLLOUT or POLLRDNORM or POLLWRNORM));
|
||||
end;
|
||||
|
@ -585,7 +630,9 @@ begin
|
|||
begin
|
||||
error:=kern_sigprocmask(td, SIG_SETMASK, uset, @td^.td_oldsigmask, 0);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
td^.td_pflags:=td^.td_pflags or TDP_OLDMASK;
|
||||
{
|
||||
* Make sure that ast() is called on Exitto
|
||||
|
@ -613,19 +660,27 @@ begin
|
|||
begin
|
||||
error:=copyin(uts, @ts, sizeof(ts));
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
TIMESPEC_TO_TIMEVAL(@tv, @ts);
|
||||
tvp:=@tv;
|
||||
end else
|
||||
begin
|
||||
tvp:=nil;
|
||||
end;
|
||||
if (sm<>nil) then
|
||||
begin
|
||||
error:=copyin(sm, @_set, sizeof(_set));
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
uset:=@_set;
|
||||
end else
|
||||
begin
|
||||
uset:=nil;
|
||||
end;
|
||||
Exit(kern_pselect(nd, uin, uou, uex, tvp, uset, NFDBITS));
|
||||
end;
|
||||
|
||||
|
@ -639,7 +694,9 @@ begin
|
|||
begin
|
||||
error:=copyin(utv, @tv, sizeof(tv));
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
tvp:=@tv;
|
||||
end else
|
||||
tvp:=nil;
|
||||
|
@ -663,7 +720,9 @@ var
|
|||
bits:Byte;
|
||||
begin
|
||||
if (nd >= ndu) or (fd_in=nil) then
|
||||
begin
|
||||
Exit(0);
|
||||
end;
|
||||
|
||||
oaddr:=nil;
|
||||
bits:=0; { silence gcc }
|
||||
|
@ -675,12 +734,16 @@ begin
|
|||
begin
|
||||
res:=fubyte(addr^);
|
||||
if (res=-1) then
|
||||
begin
|
||||
Exit(EFAULT);
|
||||
end;
|
||||
oaddr:=addr;
|
||||
bits:=res;
|
||||
end;
|
||||
if ((bits and (1 shl (i mod NBBY)))<>0) then
|
||||
begin
|
||||
Exit(EBADF);
|
||||
end;
|
||||
end;
|
||||
Exit(0);
|
||||
end;
|
||||
|
@ -714,7 +777,9 @@ var
|
|||
begin
|
||||
error2:=copyout(@obits[x], name, ncpubytes);
|
||||
if (error2<>0) then
|
||||
begin
|
||||
error:=error2;
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
|
||||
|
@ -731,13 +796,19 @@ begin
|
|||
|
||||
error:=select_check_badfd(fd_in, nd, ndu, abi_nfdbits);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
error:=select_check_badfd(fd_ou, nd, ndu, abi_nfdbits);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
error:=select_check_badfd(fd_ex, nd, ndu, abi_nfdbits);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
|
||||
{
|
||||
* Allocate just enough bits for the non-nil fd_sets. Use the
|
||||
|
@ -749,11 +820,17 @@ begin
|
|||
nbufbytes:=0;
|
||||
|
||||
if (fd_in<>nil) then
|
||||
begin
|
||||
Inc(nbufbytes,2 * ncpbytes);
|
||||
end;
|
||||
if (fd_ou<>nil) then
|
||||
begin
|
||||
Inc(nbufbytes,2 * ncpbytes);
|
||||
end;
|
||||
if (fd_ex<>nil) then
|
||||
begin
|
||||
Inc(nbufbytes,2 * ncpbytes);
|
||||
end;
|
||||
|
||||
if (nbufbytes <= sizeof(s_selbits)) then
|
||||
selbits:=@s_selbits[0]
|
||||
|
@ -789,12 +866,16 @@ begin
|
|||
repeat
|
||||
error:=selscan(td, @ibits, @obits, nd);
|
||||
if (error<>0) or (td^.td_retval[0]<>0) then
|
||||
begin
|
||||
break;
|
||||
end;
|
||||
if (atv<>0) then
|
||||
begin
|
||||
rtv:=get_unit_uptime;
|
||||
if (rtv>=atv) then
|
||||
begin
|
||||
break;
|
||||
end;
|
||||
ttv:=atv-rtv;
|
||||
|
||||
if (ttv>24*60*60*hz) then
|
||||
|
@ -804,19 +885,27 @@ begin
|
|||
end;
|
||||
error:=seltdwait(td, timo);
|
||||
if (error<>0) then
|
||||
begin
|
||||
break;
|
||||
end;
|
||||
error:=selrescan(td, @ibits, @obits);
|
||||
if (error<>0) or (td^.td_retval[0]<>0) then
|
||||
begin
|
||||
break;
|
||||
end;
|
||||
until false;
|
||||
seltdclear(td);
|
||||
|
||||
done:
|
||||
{ select is not restarted after signals... }
|
||||
if (error=ERESTART) then
|
||||
begin
|
||||
error:=EINTR;
|
||||
end;
|
||||
if (error=EWOULDBLOCK) then
|
||||
begin
|
||||
error:=0;
|
||||
end;
|
||||
|
||||
if (error=0) then
|
||||
begin
|
||||
|
@ -826,7 +915,9 @@ done:
|
|||
end;
|
||||
|
||||
if (selbits<>@s_selbits[0]) then
|
||||
begin
|
||||
FreeMem(selbits);
|
||||
end;
|
||||
|
||||
Exit(error);
|
||||
end;
|
||||
|
@ -902,7 +993,9 @@ var
|
|||
begin
|
||||
fp:=fget_unlocked(fd);
|
||||
if (fp=nil) then
|
||||
begin
|
||||
Exit(EBADF);
|
||||
end;
|
||||
{
|
||||
* If the file descriptor is for a capability, test rights and use
|
||||
* the file descriptor references by the capability.
|
||||
|
@ -958,7 +1051,9 @@ begin
|
|||
end;
|
||||
error:=getselfd_cap(fd, @fp);
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
idx:=fd div NFDBITS;
|
||||
bit:=fd_mask(1) shl (fd mod NFDBITS);
|
||||
ev:=fo_poll(fp, selflags(ibits, idx, bit));
|
||||
|
@ -1032,16 +1127,22 @@ var
|
|||
ni:QWORD;
|
||||
begin
|
||||
if (nfds > maxfilesperproc) and (nfds > FD_SETSIZE) then
|
||||
begin
|
||||
Exit(EINVAL);
|
||||
end;
|
||||
td:=curkthread;
|
||||
ni:=nfds * sizeof(t_pollfd);
|
||||
|
||||
if (ni > sizeof(smallbits)) then
|
||||
bits:=AllocMem(ni)
|
||||
else
|
||||
bits:=@smallbits;
|
||||
|
||||
error:=copyin(fds, bits, ni);
|
||||
if (error<>0) then
|
||||
begin
|
||||
goto done;
|
||||
end;
|
||||
if (timeout<>INFTIM) then
|
||||
begin
|
||||
atv:=USEC_TO_UNIT(_msec2usec(timeout));
|
||||
|
@ -1072,28 +1173,40 @@ begin
|
|||
end;
|
||||
error:=seltdwait(td, timo);
|
||||
if (error<>0) then
|
||||
begin
|
||||
break;
|
||||
end;
|
||||
error:=pollrescan(td);
|
||||
if (error<>0) or (td^.td_retval[0]<>0) then
|
||||
begin
|
||||
break;
|
||||
end;
|
||||
until false;
|
||||
seltdclear(td);
|
||||
|
||||
done:
|
||||
{ poll is not restarted after signals... }
|
||||
if (error=ERESTART) then
|
||||
begin
|
||||
error:=EINTR;
|
||||
end;
|
||||
if (error=EWOULDBLOCK) then
|
||||
begin
|
||||
error:=0;
|
||||
end;
|
||||
if (error=0) then
|
||||
begin
|
||||
error:=_pollout(td, bits, fds, nfds);
|
||||
if (error<>0) then
|
||||
begin
|
||||
goto _out;
|
||||
end;
|
||||
end;
|
||||
_out:
|
||||
if (ni > sizeof(smallbits)) then
|
||||
begin
|
||||
FreeMem(bits);
|
||||
end;
|
||||
Exit(error);
|
||||
end;
|
||||
|
||||
|
@ -1129,7 +1242,9 @@ begin
|
|||
if (cap_funwrap(fp, CAP_POLL_EVENT, @fp)<>0) then
|
||||
begin
|
||||
if (fp<>nil) then
|
||||
begin
|
||||
fdrop(fp);
|
||||
end;
|
||||
//
|
||||
fd^.revents:=POLLNVAL;
|
||||
Inc(n);
|
||||
|
@ -1144,7 +1259,9 @@ begin
|
|||
}
|
||||
fd^.revents:=fo_poll(fp, fd^.events);
|
||||
if (fd^.revents<>0) then
|
||||
begin
|
||||
Inc(n);
|
||||
end;
|
||||
//
|
||||
fdrop(fp);
|
||||
//
|
||||
|
@ -1168,9 +1285,13 @@ begin
|
|||
begin
|
||||
error:=copyout(@fds^.revents, @ufds^.revents, sizeof(ufds^.revents));
|
||||
if (error<>0) then
|
||||
begin
|
||||
Exit(error);
|
||||
end;
|
||||
if (fds^.revents<>0) then
|
||||
begin
|
||||
Inc(n);
|
||||
end;
|
||||
Inc(fds);
|
||||
Inc(ufds);
|
||||
end;
|
||||
|
@ -1217,14 +1338,20 @@ begin
|
|||
* set simultaneously with POLLHUP.
|
||||
}
|
||||
if ((fds^.revents and POLLHUP)<>0) then
|
||||
begin
|
||||
fds^.revents:=fds^.revents and (not POLLOUT);
|
||||
end;
|
||||
|
||||
if (fds^.revents<>0) then
|
||||
begin
|
||||
Inc(n);
|
||||
end;
|
||||
end;
|
||||
//
|
||||
if (fp<>nil) then
|
||||
begin
|
||||
fdrop(fp);
|
||||
end;
|
||||
end;
|
||||
//
|
||||
Inc(i);
|
||||
|
@ -1245,11 +1372,15 @@ var
|
|||
begin
|
||||
stp:=td^.td_sel;
|
||||
if (stp^.st_free1=nil) then
|
||||
begin
|
||||
stp^.st_free1:=AllocMem(SizeOf(t_selfd));
|
||||
end;
|
||||
stp^.st_free1^.sf_td:=stp;
|
||||
stp^.st_free1^.sf_cookie:=cookie;
|
||||
if (stp^.st_free2=nil) then
|
||||
begin
|
||||
stp^.st_free2:=AllocMem(SizeOf(t_selfd));
|
||||
end;
|
||||
stp^.st_free2^.sf_td:=stp;
|
||||
stp^.st_free2^.sf_cookie:=cookie;
|
||||
end;
|
||||
|
@ -1259,7 +1390,9 @@ begin
|
|||
STAILQ_REMOVE(@stp^.st_selq,sfp,@sfp^.sf_link);
|
||||
mtx_lock(sfp^.sf_mtx^);
|
||||
if (sfp^.sf_si<>nil) then
|
||||
begin
|
||||
TAILQ_REMOVE(@sfp^.sf_si^.si_tdlist,sfp,@sfp^.sf_threads);
|
||||
end;
|
||||
mtx_unlock(sfp^.sf_mtx^);
|
||||
FreeMem(sfp);
|
||||
end;
|
||||
|
@ -1292,19 +1425,23 @@ begin
|
|||
* Don't record when doing a rescan.
|
||||
}
|
||||
if ((stp^.st_flags and SELTD_RESCAN)<>0) then
|
||||
begin
|
||||
Exit;
|
||||
end;
|
||||
{
|
||||
* Grab one of the preallocated descriptors.
|
||||
}
|
||||
sfp:=stp^.st_free1;
|
||||
if (sfp<>nil) then
|
||||
begin
|
||||
stp^.st_free1:=nil
|
||||
else
|
||||
end else
|
||||
begin
|
||||
sfp:=stp^.st_free2;
|
||||
if (sfp<>nil) then
|
||||
begin
|
||||
stp^.st_free2:=nil
|
||||
else
|
||||
end else
|
||||
begin
|
||||
Assert(false,'selrecord: No free selfd on selq');
|
||||
Exit;
|
||||
|
@ -1312,7 +1449,9 @@ begin
|
|||
end;
|
||||
mtxp:=sip^.si_mtx;
|
||||
if (mtxp=nil) then
|
||||
begin
|
||||
mtxp:=mtx_pool_find(mtxpool_select, sip);
|
||||
end;
|
||||
{
|
||||
* Initialize the sfp and queue it in the thread.
|
||||
}
|
||||
|
@ -1359,7 +1498,9 @@ var
|
|||
begin
|
||||
{ If it's not initialized there can't be any waiters. }
|
||||
if (sip^.si_mtx=nil) then
|
||||
begin
|
||||
Exit;
|
||||
end;
|
||||
{
|
||||
* Locking the selinfo locks all selfds associated with it.
|
||||
}
|
||||
|
@ -1393,7 +1534,9 @@ var
|
|||
begin
|
||||
stp:=td^.td_sel;
|
||||
if (stp<>nil) then
|
||||
begin
|
||||
goto _out;
|
||||
end;
|
||||
stp:=AllocMem(sizeof(t_seltd));
|
||||
td^.td_sel:=stp;
|
||||
mtx_init(stp^.st_mtx, 'sellck');
|
||||
|
@ -1423,10 +1566,12 @@ begin
|
|||
mtx_unlock(stp^.st_mtx);
|
||||
Exit(0);
|
||||
end;
|
||||
|
||||
if (timo > 0) then
|
||||
error:=_cv_timedwait_sig(@stp^.st_wait, @stp^.st_mtx, timo)
|
||||
else
|
||||
error:=_cv_wait_sig(@stp^.st_wait, @stp^.st_mtx);
|
||||
|
||||
mtx_unlock(stp^.st_mtx);
|
||||
|
||||
Exit(error);
|
||||
|
@ -1438,11 +1583,17 @@ var
|
|||
begin
|
||||
stp:=td^.td_sel;
|
||||
if (stp=nil) then
|
||||
begin
|
||||
Exit;
|
||||
end;
|
||||
if (stp^.st_free1<>nil) then
|
||||
begin
|
||||
FreeMem(stp^.st_free1);
|
||||
end;
|
||||
if (stp^.st_free2<>nil) then
|
||||
begin
|
||||
FreeMem(stp^.st_free2);
|
||||
end;
|
||||
td^.td_sel:=nil;
|
||||
FreeMem(stp);
|
||||
end;
|
||||
|
|
Loading…
Reference in New Issue