Go to the documentation of this file.00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 
00014 
00015 
00016 
00017 
00018 
00019 
00020 
00021 
00022 
00023 
00024 
00025 
00026 
00027 
00028 
00029 
00030 
00031 #if !defined (_I_AIO_h_)
00032 #define _I_AIO_h_
00033 
00034 #include "libts.h"
00035 #include "I_EventSystem.h"
00036 #include "I_RecProcess.h"
00037 
00038 #define AIO_MODULE_MAJOR_VERSION 1
00039 #define AIO_MODULE_MINOR_VERSION 0
00040 #define AIO_MODULE_VERSION       makeModuleVersion(AIO_MODULE_MAJOR_VERSION,\
00041                                                    AIO_MODULE_MINOR_VERSION,\
00042                                                    PUBLIC_MODULE_HEADER)
00043 
00044 #define AIO_EVENT_DONE           (AIO_EVENT_EVENTS_START+0)
00045 
00046 #define AIO_MODE_AIO             0
00047 #define AIO_MODE_SYNC            1
00048 #define AIO_MODE_THREAD          2
00049 #define AIO_MODE_NATIVE          3
00050 
00051 #if TS_USE_LINUX_NATIVE_AIO
00052 #define AIO_MODE                 AIO_MODE_NATIVE
00053 #else
00054 #define AIO_MODE                 AIO_MODE_THREAD
00055 #endif
00056 
00057 #define LIO_READ        0x1
00058 #define LIO_WRITE       0x2
00059 
00060 #if AIO_MODE == AIO_MODE_NATIVE
00061 
00062 #include <libaio.h>
00063 
00064 #define MAX_AIO_EVENTS 1024
00065 
00066 typedef struct iocb ink_aiocb_t;
00067 typedef struct io_event ink_io_event_t;
00068 
00069 
00070 #define aio_nbytes  u.c.nbytes
00071 #define aio_offset  u.c.offset
00072 #define aio_buf     u.c.buf
00073 
00074 #else
00075 
00076 typedef struct ink_aiocb
00077 {
00078   int aio_fildes;
00079   volatile void *aio_buf;       
00080   size_t aio_nbytes;            
00081   off_t aio_offset;             
00082 
00083   int aio_reqprio;              
00084   int aio_lio_opcode;           
00085   int aio_state;                
00086   int aio__pad[1];              
00087 } ink_aiocb_t;
00088 
00089 bool ink_aio_thread_num_set(int thread_num);
00090 
00091 #endif
00092 
00093 
00094 #define AIO_CALLBACK_THREAD_ANY ((EThread*)0) // any regular event thread
00095 #define AIO_CALLBACK_THREAD_AIO ((EThread*)-1)
00096 
00097 #define AIO_LOWEST_PRIORITY      0
00098 #define AIO_DEFAULT_PRIORITY     AIO_LOWEST_PRIORITY
00099 
00100 struct AIOCallback: public Continuation
00101 {
00102   
00103   ink_aiocb_t aiocb;
00104   Action action;
00105   EThread *thread;
00106   AIOCallback *then;
00107   
00108   int64_t aio_result;
00109 
00110   int ok();
00111   AIOCallback() : thread(AIO_CALLBACK_THREAD_ANY), then(0) {
00112     aiocb.aio_reqprio = AIO_DEFAULT_PRIORITY;
00113   }
00114 };
00115 
00116 #if AIO_MODE == AIO_MODE_NATIVE
00117 
00118 struct AIOVec: public Continuation
00119 {
00120   Action action;
00121   int size;
00122   int completed;
00123   AIOCallback *first;
00124 
00125   AIOVec(int sz, AIOCallback *c): Continuation(new_ProxyMutex()), size(sz), completed(0), first(c)
00126   {
00127     action = c->action;
00128     SET_HANDLER(&AIOVec::mainEvent);
00129   }
00130 
00131   int mainEvent(int event, Event *e);
00132 };
00133 
00134 struct DiskHandler: public Continuation
00135 {
00136   Event *trigger_event;
00137   io_context_t ctx;
00138   ink_io_event_t events[MAX_AIO_EVENTS];
00139   Que(AIOCallback, link) ready_list;
00140   Que(AIOCallback, link) complete_list;
00141   int startAIOEvent(int event, Event *e);
00142   int mainAIOEvent(int event, Event *e);
00143   DiskHandler() {
00144     SET_HANDLER(&DiskHandler::startAIOEvent);
00145     memset(&ctx, 0, sizeof(ctx));
00146     int ret = io_setup(MAX_AIO_EVENTS, &ctx);
00147     if (ret < 0) {
00148       perror("io_setup error");
00149     }
00150   }
00151 };
00152 #endif
00153 
00154 void ink_aio_init(ModuleVersion version);
00155 int ink_aio_start();
00156 void ink_aio_set_callback(Continuation * error_callback);
00157 
00158 int ink_aio_read(AIOCallback *op, int fromAPI = 0);   
00159 int ink_aio_write(AIOCallback *op, int fromAPI = 0);
00160 int ink_aio_readv(AIOCallback *op, int fromAPI = 0);   
00161 int ink_aio_writev(AIOCallback *op, int fromAPI = 0);
00162 AIOCallback *new_AIOCallback(void);
00163 #endif