diff options
Diffstat (limited to 'erts/emulator/drivers/common/efile_drv.c')
-rw-r--r-- | erts/emulator/drivers/common/efile_drv.c | 171 |
1 files changed, 29 insertions, 142 deletions
diff --git a/erts/emulator/drivers/common/efile_drv.c b/erts/emulator/drivers/common/efile_drv.c index 509c4fe48c..7e194a3787 100644 --- a/erts/emulator/drivers/common/efile_drv.c +++ b/erts/emulator/drivers/common/efile_drv.c @@ -629,113 +629,6 @@ static struct t_data *cq_deq(file_descriptor *desc) { return d; } - -/********************************************************************* - * Command queue functions - */ - -static ErlDrvTermData am_ok; -static ErlDrvTermData am_error; -static ErlDrvTermData am_efile_reply; - -#define INIT_ATOM(NAME) am_ ## NAME = driver_mk_atom(#NAME) - -#define LOAD_ATOM_CNT 2 -#define LOAD_ATOM(vec, i, atom) \ - (((vec)[(i)] = ERL_DRV_ATOM), \ - ((vec)[(i)+1] = (atom)), \ - ((i)+LOAD_ATOM_CNT)) - -#define LOAD_INT_CNT 2 -#define LOAD_INT(vec, i, val) \ - (((vec)[(i)] = ERL_DRV_INT), \ - ((vec)[(i)+1] = (ErlDrvTermData)(val)), \ - ((i)+LOAD_INT_CNT)) - -#define LOAD_INT64_CNT 2 -#define LOAD_INT64(vec, i, val) \ - (((vec)[(i)] = ERL_DRV_INT64), \ - ((vec)[(i)+1] = (ErlDrvTermData)(val)), \ - ((i)+LOAD_INT64_CNT)) - -#define LOAD_PORT_CNT 2 -#define LOAD_PORT(vec, i, port) \ - (((vec)[(i)] = ERL_DRV_PORT), \ - ((vec)[(i)+1] = (port)), \ - ((i)+LOAD_PORT_CNT)) - -#define LOAD_PID_CNT 2 -#define LOAD_PID(vec, i, pid) \ - (((vec)[(i)] = ERL_DRV_PID), \ - ((vec)[(i)+1] = (pid)), \ - ((i)+LOAD_PID_CNT)) - -#define LOAD_TUPLE_CNT 2 -#define LOAD_TUPLE(vec, i, size) \ - (((vec)[(i)] = ERL_DRV_TUPLE), \ - ((vec)[(i)+1] = (size)), \ - ((i)+LOAD_TUPLE_CNT)) - -/* send: -** {efile_reply, Pid, Port, {ok, int64()}} -*/ - -static int ef_send_ok_int64(file_descriptor *desc, ErlDrvTermData caller, - ErlDrvSInt64 *n) -{ - ErlDrvTermData spec[2*LOAD_ATOM_CNT + LOAD_PID_CNT + LOAD_PORT_CNT - + LOAD_INT64_CNT + 2*LOAD_TUPLE_CNT]; - int i = 0; - - i = LOAD_ATOM(spec, i, am_efile_reply); - i = LOAD_PID(spec, i, caller); - i = LOAD_PORT(spec, i, driver_mk_port(desc->port)); - i = LOAD_ATOM(spec, i, am_ok); - i = LOAD_INT64(spec, i, n); - i = LOAD_TUPLE(spec, i, 2); - i = LOAD_TUPLE(spec, i, 4); - ASSERT(i == sizeof(spec)/sizeof(*spec)); - - return driver_send_term(desc->port, caller, spec, i); -} - -static ErlDrvTermData error_atom(int err) -{ - char errstr[256]; - char* s; - char* t; - - for (s = erl_errno_id(err), t = errstr; *s; s++, t++) - *t = tolower(*s); - *t = '\0'; - return driver_mk_atom(errstr); -} - -/* send: -** {efile_reply, Pid, Port, {error, posix_error()} -*/ - -static int ef_send_posix_error(file_descriptor *desc, ErlDrvTermData caller, - int e) -{ - ErlDrvTermData spec[3*LOAD_ATOM_CNT + LOAD_PID_CNT + LOAD_PORT_CNT - + 2*LOAD_TUPLE_CNT]; - int i = 0; - - i = LOAD_ATOM(spec, i, am_efile_reply); - i = LOAD_PID(spec, i, caller); - i = LOAD_PORT(spec, i, driver_mk_port(desc->port)); - i = LOAD_ATOM(spec, i, am_error); - /* TODO: safe? set of error codes should be limited and safe */ - i = LOAD_ATOM(spec, i, error_atom(e)); - i = LOAD_TUPLE(spec, i, 2); - i = LOAD_TUPLE(spec, i, 4); - ASSERT(i == sizeof(spec)/sizeof(*spec)); - - desc->caller = 0; - return driver_send_term(desc->port, caller, spec, i); -} - /********************************************************************* * Driver entry point -> init */ @@ -751,10 +644,6 @@ file_init(void) : 0); driver_system_info(&sys_info, sizeof(ErlDrvSysInfo)); - INIT_ATOM(ok); - INIT_ATOM(error); - INIT_ATOM(efile_reply); - return 0; } @@ -1871,7 +1760,7 @@ static void do_sendfile(file_descriptor *d) ERL_DRV_USE|ERL_DRV_WRITE, 1); } else { printf("==> sendfile DONE eagain=%d\n", d->sendfile.eagain); - ef_send_ok_int64(d, d->caller, &d->sendfile.written); + reply_Uint(d, d->sendfile.written); } } else if (errInfo.posix_errno == EAGAIN || errInfo.posix_errno == EINTR) { if (chunksize > 0) { @@ -2301,8 +2190,6 @@ file_async_ready(ErlDrvData e, ErlDrvThreadData data) free_preadv(data); break; case FILE_SENDFILE: - /* Return 'ok' and let prim_file:sendfile wait for message */ - reply_ok(desc); driver_select(desc->port, (ErlDrvEvent)desc->sendfile.out_fd, ERL_DRV_USE|ERL_DRV_WRITE, 1); free_data(data); @@ -2654,34 +2541,6 @@ file_output(ErlDrvData e, char* buf, int count) goto done; } - case FILE_SENDFILE: - { - d = EF_SAFE_ALLOC(sizeof(struct t_data)); - d->fd = fd; - d->command = command; - d->invoke = invoke_sendfile; - d->free = free_data; - d->level = 2; - desc->sendfile.out_fd = get_int32((uchar*) buf); - /* TODO: are off_t and size_t 64bit on all platforms? - off_t is 32bit on win32 msvc. maybe configurable in msvc. - Maybe use '#if SIZEOF_SIZE_T == 4'? */ - desc->sendfile.offset = get_int64(((uchar*) buf) - + sizeof(Sint32)); - desc->sendfile.count = get_int64(((uchar*) buf) - + sizeof(Sint32) - + sizeof(Sint64)); - desc->sendfile.chunksize = get_int64(((uchar*) buf) - + sizeof(Sint32) - + 2*sizeof(Sint64)); - desc->sendfile.written = 0; - desc->sendfile.eagain = 0; - /* TODO: shouldn't d->command be enough? */ - desc->command = command; - desc->caller = driver_caller(desc->port); - goto done; - } - } /* @@ -3475,6 +3334,34 @@ file_outputv(ErlDrvData e, ErlIOVec *ev) { goto done; } /* case FILE_OPT_DELAYED_WRITE: */ } ASSERT(0); goto done; /* case FILE_SETOPT: */ + case FILE_SENDFILE: + { + struct t_data *d; + d = EF_SAFE_ALLOC(sizeof(struct t_data)); + d->fd = desc->fd; + d->command = command; + d->invoke = invoke_sendfile; + d->free = free_data; + d->level = 2; + desc->sendfile.out_fd = get_int32((uchar*) buf); + /* TODO: are off_t and size_t 64bit on all platforms? + off_t is 32bit on win32 msvc. maybe configurable in msvc. + Maybe use '#if SIZEOF_SIZE_T == 4'? */ + desc->sendfile.offset = get_int64(((uchar*) buf) + + sizeof(Sint32)); + desc->sendfile.count = get_int64(((uchar*) buf) + + sizeof(Sint32) + + sizeof(Sint64)); + desc->sendfile.chunksize = get_int64(((uchar*) buf) + + sizeof(Sint32) + + 2*sizeof(Sint64)); + desc->sendfile.written = 0; + desc->sendfile.eagain = 0; + /* TODO: shouldn't d->command be enough? */ + desc->command = command; + desc->caller = driver_caller(desc->port); + goto done; + } } /* switch(command) */ |