MCPcopy Create free account
hub / github.com/bendudson/EuraliOS / rcall

Function rcall

euralios_std/src/message.rs:165–231  ·  view source on GitHub ↗

Remote call. Wrapper around send_receive syscall

(
    handle: &CommHandle,
    data1: u64,
    data2: MessageData,
    data3: MessageData,
    expect_rdata1: Option<u64>
)

Source from the content-addressed store, hash-verified

163/// Remote call.
164/// Wrapper around send_receive syscall
165pub fn rcall(
166 handle: &CommHandle,
167 data1: u64,
168 data2: MessageData,
169 data3: MessageData,
170 expect_rdata1: Option<u64>
171) -> Result<(u64, MessageData, MessageData), (SyscallError, Message)> {
172
173 let mut message = match (data2, data3) {
174 (MessageData::Value(value2), MessageData::Value(value3)) => Message::Short(data1, value2, value3),
175 (data2, data3) => Message::Long(data1, data2, data3)
176 };
177
178 const MAX_RETRIES: usize = 100;
179
180 let mut retry = 0;
181 loop {
182 // Try sending
183 let result = syscalls::send_receive(
184 handle,
185 message);
186
187 match result {
188 Err((syscalls::SYSCALL_ERROR_SEND_BLOCKING, ret_message)) |
189 Err((syscalls::SYSCALL_ERROR_RECV_BLOCKING, ret_message)) => {
190 // Rendezvous blocked => Wait and try again
191
192 message = ret_message; // Handles may have changed
193
194 retry += 1;
195 if retry > MAX_RETRIES {
196 // Give up
197 return Err((syscalls::SYSCALL_ERROR_SEND_BLOCKING, message));
198 }
199
200 // Let another thread run
201 syscalls::thread_yield();
202
203 continue; // Go around for another try
204 }
205 Err(err_message) => {
206 return Err(err_message);
207 }
208 Ok(Message::Short(ERROR, sys_err, rdata3)) => {
209 return Err((SyscallError::new(sys_err), Message::Short(ERROR, sys_err, rdata3)));
210 }
211 Ok(Message::Short(rdata1, rdata2, rdata3)) => {
212 if let Some(rd1) = expect_rdata1 {
213 // Filter on first argument
214 if rdata1 != rd1 {
215 return Err((SyscallError::new(0), Message::Short(rdata1, rdata2, rdata3)));
216 }
217 }
218 return Ok((rdata1, rdata2.into(), rdata3.into()));
219 }
220 Ok(Message::Long(rdata1, rdata2, rdata3)) => {
221 if let Some(rd1) = expect_rdata1 {
222 // Filter on first argument

Callers 14

newMethod · 0.85
gopherFunction · 0.85
mainFunction · 0.85
_openFunction · 0.85
queryMethod · 0.85
rcallMethod · 0.85
writeMethod · 0.85
read_to_endMethod · 0.85
write_strMethod · 0.85
mainFunction · 0.85
receiveMethod · 0.85
mainFunction · 0.85

Calls 2

send_receiveFunction · 0.85
thread_yieldFunction · 0.85

Tested by

no test coverage detected