freebsd.pas 8.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299
  1. Unit FreeBSD;
  2. {
  3. This file is part of the Free Pascal run time library.
  4. (c) 2005 by Marco van de Voort
  5. member of the Free Pascal development team.
  6. based on the sendfile conversion of Ales Katona 30.01.2006
  7. See the file COPYING.FPC, included in this distribution,
  8. for details about the copyright.
  9. Unit for FreeBSD specific calls. Calls may move to "BSD" unit in time,
  10. if turns out that more BSDs include them.
  11. This program is distributed in the hope that it will be useful,
  12. but WITHOUT ANY WARRANTY;without even the implied warranty of
  13. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  14. }
  15. {$IFDEF FPC}
  16. {$PACKRECORDS C}
  17. {$inline on}
  18. {$Macro On}
  19. {$ifdef FPC_USE_LIBC}
  20. {$define extdecl:=cdecl; external 'c'}
  21. {$else}
  22. {$define extdecl:=inline}
  23. {$endif}
  24. {$ENDIF}
  25. interface
  26. uses
  27. BaseUnix;
  28. const
  29. SF_NODISKIO = $00000001; // don't wait for disk IO, similar to non-blocking socket setting
  30. // kernel threads
  31. KSE_VER_0 = 0;
  32. KSE_VERSION = KSE_VER_0;
  33. {* These flags are kept in km_flags *}
  34. KMF_NOUPCALL = $01;
  35. KMF_NOCOMPLETED = $02;
  36. KMF_DONE = $04;
  37. KMF_BOUND = $08;
  38. KMF_WAITSIGEVENT = $10;
  39. {* These flags are kept in tm_flags *}
  40. TMF_NOUPCALL = $01;
  41. {* These flags are kept in tm_dlfags *}
  42. TMDF_SSTEP = $01;
  43. TMDF_SUSPEND = $02;
  44. {* Flags for kse_switchin *}
  45. KSE_SWITCHIN_SETTMBX = $01;
  46. {* Commands for kse_thr_interrupt *}
  47. KSE_INTR_INTERRUPT = 1;
  48. KSE_INTR_RESTART = 2;
  49. KSE_INTR_SENDSIG = 3;
  50. KSE_INTR_SIGEXIT = 4;
  51. KSE_INTR_DBSUSPEND = 5;
  52. KSE_INTR_EXECVE = 6;
  53. {$i ucontexth.inc} // required for kse threads
  54. Type
  55. SF_HDTR = record
  56. headers: PIOVec; {* pointer to an array of header struct iovec's *}
  57. hdr_cnt: cint; {* number of header iovec's *}
  58. trailers: PIOVec; {* pointer to an array of trailer struct iovec's *}
  59. trl_cnt: cint; {* number of trailer iovec's *}
  60. end;
  61. TSF_HDTR = SF_HDTR;
  62. PSF_HDTR = ^TSF_HDTR;
  63. kld_file_stat = record
  64. Version: cInt; {* set to sizeof(linker_file_stat) *}
  65. Name: array[0..MAXPATHLEN-1] of Char;
  66. Refs: cInt;
  67. ID: cInt;
  68. Address: pChar; {* load address *}
  69. Size: size_t; {* size in bytes *}
  70. end;
  71. tkld_file_stat = kld_file_stat;
  72. pkld_file_stat = ^kld_file_stat;
  73. TKldFileStat = kld_file_stat;
  74. PKldFileStat = ^kld_file_stat;
  75. kld_sym_lookup = record
  76. Version: cInt; {* sizeof(struct kld_sym_lookup) *}
  77. SymName: pChar; {* Symbol name we are looking up *}
  78. SymValue: culong;
  79. SymSize: size_t;
  80. end;
  81. tkld_sym_lookup = kld_sym_lookup;
  82. pkld_sym_lookup = ^kld_sym_lookup;
  83. TKldSymLookup = kld_sym_lookup;
  84. PKldSymLookup = ^kld_sym_lookup;
  85. // kernel threads
  86. pkse_mailbox = ^kse_mailbox;
  87. pkse_func_t = ^kse_func_t;
  88. kse_func_t = procedure(mbx: pkse_mailbox);
  89. TKseFunc = kse_func_t;
  90. PKseFunc = pkse_func_t;
  91. {*
  92. * Thread mailbox.
  93. *
  94. * This describes a user thread to the kernel scheduler.
  95. *}
  96. pkse_thr_mailbox = ^kse_thr_mailbox;
  97. kse_thr_mailbox = record
  98. tm_context: ucontext_t; {* User and machine context *}
  99. tm_flags: cuint32; {* Thread flags *}
  100. tm_next: pkse_thr_mailbox; {* Next thread in list *}
  101. tm_udata: Pointer; {* For use by the UTS *}
  102. tm_uticks: cuint32; {* Time in userland *}
  103. tm_sticks: cuint32; {* Time in kernel *}
  104. tm_syncsig: siginfo_t;
  105. tm_dflags: cuint32; {* Debug flags *}
  106. tm_lwp: lwpid_t; {* kernel thread UTS runs on *}
  107. __spare__: array [0..5] of cuint32;
  108. end;
  109. TKseThrMailBox = kse_thr_mailbox;
  110. PKseThrMailBox = pkse_thr_mailbox;
  111. {*
  112. * KSE mailbox.
  113. *
  114. * Communication path between the UTS and the kernel scheduler specific to
  115. * a single KSE.
  116. *}
  117. kse_mailbox = record
  118. km_version: cuint32; {* Mailbox version *}
  119. km_curthread: pkse_thr_mailbox; {* Currently running thread *}
  120. km_completed: pkse_thr_mailbox; {* Threads back from kernel *}
  121. km_sigscaught: sigset_t; {* Caught signals *}
  122. km_flags: cuint32; {* Mailbox flags *}
  123. km_func: pkse_func_t; {* UTS function *}
  124. km_stack: stack_t; {* UTS stack *}
  125. km_udata: Pointer; {* For use by the UTS *}
  126. km_timeofday: TTimeSpec; {* Time of day *}
  127. km_quantum: cuint32; {* Upcall quantum in msecs *}
  128. km_lwp: lwpid_t; {* kernel thread UTS runs on *}
  129. __spare2__: array[0..6] of cuint32
  130. end;
  131. TKseMailBox = kse_mailbox;
  132. PKseMailBox = pkse_mailbox;
  133. function sendfile(fd: cint; s: cint; Offset: TOff; nBytes: TSize;
  134. HDTR: PSF_HDTR; sBytes: POff; Flags: cint): cint; extdecl;
  135. // Kernel modules support
  136. function kldload(FileName: pChar): cInt; extdecl;
  137. function kldunload(fileid: cInt): cInt; extdecl;
  138. function kldfind(FileName: pChar): cInt; extdecl;
  139. function kldnext(fileid: cInt): cInt; extdecl;
  140. function kldstat(fileid: cInt; kld_file_stat: pKldFileStat): cInt; extdecl;
  141. function kldfirstmod(fileid: cInt): cInt; extdecl;
  142. function kldsym(fileid: cInt; command: cInt; data: PKldSymLookup): cInt; extdecl;
  143. // kernel threads support
  144. function kse_exit: cInt; extdecl;
  145. function kse_wakeup(mbx: PKseMailBox): cInt; extdecl;
  146. function kse_create(mbx: PKseMailBox; newgroup: cInt): cInt; extdecl;
  147. function kse_thr_interrupt(tmbx: PKseThrMailBox; cmd: cInt; data: cLong): cInt; extdecl;
  148. function kse_release(timeout: PTimeSpec): cInt; extdecl;
  149. function kse_switchin(tmbx: PKseThrMailBox; flags: cInt): cInt; extdecl;
  150. Const
  151. MAP_FILE = $0000; { map from file (default) }
  152. MAP_ANON = $1000; { allocated from memory, swap space }
  153. MAP_RENAME = $0020; { Sun: rename private pages to file }
  154. MAP_NORESERVE = $0040; { Sun: don't reserve needed swap area }
  155. // MAP_INHERIT = $0080; { region is retained after exec. not anymore in 5.x? }
  156. // MAP_NOEXTEND = $0100; { for MAP_FILE, don't change file size. not anymore in 5.x? }
  157. MAP_HASSEMAPHORE = $0200; { region may contain semaphores }
  158. MAP_STACK = $0400; { region grows down, like a stack }
  159. MAP_NOSYNC = $0800; { page to but do not sync underlying file}
  160. MAP_NOCORE = $20000;{ dont include these pages in a coredump}
  161. implementation
  162. Uses
  163. {$ifndef FPC_USE_LIBC} SysCall; {$else} InitC; {$endif}
  164. {$IFNDEF FPC_USE_LIBC}
  165. function SendFile(fd: cint; s: cint; Offset: TOff; nBytes: TSize;
  166. HDTR: PSF_HDTR; sBytes: POff; Flags: cint): cint;
  167. begin
  168. SendFile:=Do_Syscall(syscall_nr_sendfile, fd, s,
  169. {$IFNDEF CPU64}
  170. {$IFDEF LITTLE_ENDIAN} // little endian is lo - hi
  171. Lo(Offset), Hi(Offset),
  172. {$ELSE} // big endian is hi - lo
  173. Hi(Offset), Lo(Offset),
  174. {$ENDIF}
  175. {$ELSE} // 64-bit doesn't care.
  176. TSysParam(Offset),
  177. {$ENDIF}
  178. nBytes, TSysParam(HDTR), TSysParam(sBytes), Flags);
  179. end;
  180. // kernel modules
  181. function kldload(FileName: pChar): cInt;
  182. begin
  183. kldload:=do_sysCall(syscall_nr_kldload, TSysParam(FileName));
  184. end;
  185. function kldunload(fileid: cInt): cInt;
  186. begin
  187. kldunload:=do_sysCall(syscall_nr_kldunload, TSysParam(fileid));
  188. end;
  189. function kldfind(FileName: pChar): cInt;
  190. begin
  191. kldfind:=do_sysCall(syscall_nr_kldfind, TSysParam(FileName));
  192. end;
  193. function kldnext(fileid: cInt): cInt;
  194. begin
  195. kldnext:=do_sysCall(syscall_nr_kldnext, TSysParam(fileid));
  196. end;
  197. function kldstat(fileid: cInt; kld_file_stat: pKldFileStat): cInt;
  198. begin
  199. kldstat:=do_sysCall(syscall_nr_kldstat, TSysParam(fileid),
  200. TSysParam(kld_file_stat));
  201. end;
  202. function kldfirstmod(fileid: cInt): cInt;
  203. begin
  204. kldfirstmod:=do_sysCall(syscall_nr_kldfirstmod, TSysParam(fileid));
  205. end;
  206. function kldsym(fileid: cInt; command: cInt; data: PKldSymLookup): cInt;
  207. begin
  208. kldsym:=do_sysCall(syscall_nr_kldsym, TSysParam(fileid), TSysParam(command),
  209. TSysParam(data));
  210. end;
  211. // kernel threads
  212. function kse_exit: cInt;
  213. begin
  214. kse_exit:=do_sysCall(TSysParam(syscall_nr_kse_exit));
  215. end;
  216. function kse_wakeup(mbx: PKseMailBox): cInt;
  217. begin
  218. kse_wakeup:=do_sysCall(syscall_nr_kse_wakeup, TSysParam(mbx));
  219. end;
  220. function kse_create(mbx: PKseMailBox; newgroup: cInt): cInt;
  221. begin
  222. kse_create:=do_sysCall(syscall_nr_kse_create, TSysParam(mbx),
  223. TSysParam(newgroup));
  224. end;
  225. function kse_thr_interrupt(tmbx: PKseThrMailBox; cmd: cInt; data: cLong): cInt;
  226. begin
  227. kse_thr_interrupt:=do_SysCall(syscall_nr_kse_thr_interrupt, TSysParam(tmbx),
  228. TSysParam(cmd), TSysParam(data));
  229. end;
  230. function kse_release(timeout: PTimeSpec): cInt;
  231. begin
  232. kse_release:=do_SysCall(syscall_nr_kse_release, TSysParam(timeout));
  233. end;
  234. function kse_switchin(tmbx: PKseThrMailBox; flags: cInt): cInt;
  235. begin
  236. kse_switchin:=do_SysCall(syscall_nr_kse_switchin, TSysParam(tmbx), TSysParam(flags));
  237. end;
  238. {$ENDIF}
  239. end.