1 // `suspends` contains the types that are used by the reactor API to represent blocking tasks and their results. 2 // both this and llawait() can be considered implementation details of llevents, but are exposed nonetheless. 3 // a "suspend" refers to a reason for your fiber to be on hold by the reactor 4 // not to be confused with a "suspend send", an object representing a suspend, sent to the reactor 5 // and a "suspend return" is sent back to the fiber from the reactor once it has been fulfilled. 6 module rockhopper.core.suspends; 7 8 import std.typecons : Tuple, tuple; 9 import taggedalgebraic : TaggedUnion, Void; 10 import eventcore.driver : FileFD, PipeFD, IOMode, StreamSocketFD, DatagramSocketFD; 11 12 // === SENDS === 13 14 private 15 { 16 struct SSRead(FD) 17 { 18 FD fd; 19 ulong offset; 20 ubyte[] buf; 21 IOMode ioMode; 22 } 23 24 struct SSWrite(FD) 25 { 26 FD fd; 27 ulong offset; // only used for files, ignored for pipes 28 const(ubyte)[] buf; 29 IOMode ioMode; 30 } 31 } 32 33 public 34 { 35 struct SSFileOpen 36 { 37 import eventcore.driver : FileOpenMode; 38 39 string path; 40 FileOpenMode mode; 41 } 42 43 struct SSStreamConnect 44 { 45 import std.socket : Address; 46 47 Address peerAddress; 48 Address bindAddress; 49 } 50 51 struct SSDgramSend 52 { 53 import std.socket : Address; 54 55 DatagramSocketFD fd; 56 const(ubyte)[] buf; 57 IOMode ioMode; 58 Address targetAddress; 59 } 60 61 alias SSFileRead = SSRead!FileFD; 62 alias SSPipeRead = SSRead!PipeFD; 63 alias SSStreamRead = SSRead!StreamSocketFD; 64 alias SSDgramReceive = SSRead!DatagramSocketFD; 65 alias SSFileWrite = SSWrite!FileFD; 66 alias SSPipeWrite = SSWrite!PipeFD; 67 alias SSStreamWrite = SSWrite!StreamSocketFD; 68 } 69 70 71 private union _SSRaw 72 { 73 import eventcore.driver : TimerID, ProcessID, EventID, StreamListenSocketFD; 74 import std.socket : Address; 75 76 string nsLookup; 77 EventID threadEvent; 78 SSFileOpen fileOpen; 79 FileFD fileClose; 80 SSFileRead fileRead; 81 SSPipeRead pipeRead; 82 SSFileWrite fileWrite; 83 SSPipeWrite pipeWrite; 84 ProcessID procWait; 85 int signalTrap; 86 SSStreamConnect streamConnect; 87 SSStreamRead streamRead; 88 SSDgramReceive dgramReceive; 89 SSDgramSend dgramSend; 90 SSStreamWrite streamWrite; 91 TimerID sleep; 92 // not implemented: directory watchers 93 } 94 95 public alias SuspendSend = TaggedUnion!_SSRaw; 96 97 // === RETURNS === 98 99 public 100 { 101 struct SRNsLookup 102 { 103 import eventcore.driver : DNSStatus, RefAddress; 104 105 DNSStatus status; 106 RefAddress[] addresses; 107 } 108 109 struct SRFileOpen 110 { 111 import eventcore.driver : OpenStatus; 112 113 FileFD fd; 114 OpenStatus status; 115 } 116 117 struct SRRW 118 { 119 import eventcore.driver : IOStatus; 120 121 IOStatus status; 122 // 0 if error 123 ulong bytesRWd; 124 } 125 126 struct SRStreamConnect 127 { 128 import eventcore.driver : ConnectStatus; 129 130 StreamSocketFD fd; 131 ConnectStatus status; 132 } 133 134 struct SRDgramSendReceive 135 { 136 import eventcore.driver : IOStatus, RefAddress; 137 138 IOStatus status; 139 // 0 if error 140 ulong bytesRWd; 141 RefAddress addr; 142 } 143 144 struct SRSignalTrap 145 { 146 import eventcore.driver : SignalListenID, SignalStatus; 147 148 SignalListenID slID; 149 SignalStatus status; 150 } 151 } 152 153 private union _SRRaw 154 { 155 import eventcore.driver : CloseStatus; 156 157 SRNsLookup nsLookup; 158 Void threadEvent; 159 SRFileOpen fileOpen; 160 CloseStatus fileClose; 161 SRRW rw; 162 int procWait; 163 SRSignalTrap signalTrap; 164 SRStreamConnect streamConnect; 165 SRDgramSendReceive dgramSendReceive; 166 Void sleep; 167 } 168 169 public alias SuspendReturn = TaggedUnion!_SRRaw;