ARPDAS_QNX6 1.0
|
00001 #include <errno.h> 00002 #include <stdio.h> 00003 #include <stddef.h> 00004 #include <stdlib.h> 00005 #include <string.h> 00006 #include <unistd.h> 00007 #include <sys/iofunc.h> 00008 #include <sys/dispatch.h> 00009 #include <fcntl.h> 00010 #include <ctype.h> 00011 #include <signal.h> 00012 #include "nortlib.h" 00013 #include "company.h" 00014 #include "subbusd_int.h" 00015 #include "nl_assert.h" 00016 #include "oui.h" 00017 00018 static resmgr_connect_funcs_t connect_funcs; 00019 static resmgr_io_funcs_t io_funcs; 00020 static iofunc_attr_t attr; 00021 #define DEVNAME "/dev/" COMPANY "/subbus" 00022 00023 static int SB_Shutdown = 0; 00024 00025 static int subbus_write(resmgr_context_t *ctp, io_write_t *msg, 00026 RESMGR_OCB_T *ocb) { 00027 SB_Shutdown = 1; 00028 return iofunc_write_default(ctp, msg, ocb); 00029 } 00030 00031 static int subbus_io_msg(resmgr_context_t *ctp, io_msg_t *msg, 00032 RESMGR_OCB_T *ocb) { 00033 subbusd_req_t sbdmsg; 00034 int nb, nb_exp; 00035 00036 nb = MsgRead(ctp->rcvid, &sbdmsg, sizeof(sbdmsg), 0); 00037 if ( nb < sizeof(subbusd_req_hdr_t) || 00038 sbdmsg.sbhdr.iohdr.mgrid != SUBBUSD_MGRID || 00039 sbdmsg.sbhdr.sb_kw != SB_KW) 00040 return ENOSYS; 00041 /* check the size of the incoming message */ 00042 switch ( sbdmsg.sbhdr.command ) { 00043 case SBC_WRITEACK: 00044 case SBC_WRITECACHE: 00045 nb_exp = sizeof(subbusd_req_data0); break; 00046 case SBC_SETCMDENBL: 00047 case SBC_SETCMDSTRB: 00048 case SBC_SETFAIL: 00049 case SBC_READACK: 00050 case SBC_READCACHE: 00051 nb_exp = sizeof(subbusd_req_data1); break; 00052 case SBC_READSW: 00053 case SBC_READFAIL: 00054 case SBC_GETCAPS: 00055 case SBC_TICK: 00056 case SBC_DISARM: 00057 nb_exp = 0; break; 00058 case SBC_QUIT: 00059 SB_Shutdown = 1; 00060 nb_exp = 0; break; 00061 case SBC_INTATT: 00062 nb_exp = sizeof(subbusd_req_data2); break; 00063 case SBC_INTDET: 00064 nb_exp = sizeof(subbusd_req_data3); break; 00065 case SBC_MREAD: 00066 nb_exp = 3*sizeof(unsigned short); 00067 if ( nb >= nb_exp ) { 00068 nl_assert( sbdmsg.data.d4.req_len >= nb_exp ); 00069 nb_exp = sbdmsg.data.d4.req_len; 00070 } 00071 break; 00072 default: 00073 return ENOSYS; 00074 } 00075 nb_exp += sizeof(subbusd_req_hdr_t); 00076 if ( nb < nb_exp ) 00077 nl_error( 4, "Received short message for command %d: Expected %d received %d", 00078 sbdmsg.sbhdr.command, nb_exp, nb ); 00079 incoming_sbreq( ctp->rcvid, &sbdmsg ); 00080 return (_RESMGR_NOREPLY); 00081 } 00082 00083 void sigint_handler( int sig ) { 00084 SB_Shutdown = 1; 00085 } 00086 00087 int main(int argc, char **argv) { 00088 resmgr_attr_t resmgr_attr; 00089 dispatch_t *dpp; 00090 dispatch_context_t *ctp; 00091 int id; 00092 00093 oui_init_options(argc, argv); 00094 sb_cache_init(); 00095 00096 /* initialize dispatch interface */ 00097 if((dpp = dispatch_create()) == NULL) { 00098 nl_error(3, 00099 "%s: Unable to allocate dispatch handle.\n", 00100 argv[0]); 00101 return EXIT_FAILURE; 00102 } 00103 00104 /* initialize resource manager attributes */ 00105 memset(&resmgr_attr, 0, sizeof resmgr_attr); 00106 resmgr_attr.nparts_max = 1; 00107 resmgr_attr.msg_max_size = 2048; 00108 00109 /* initialize functions for handling messages */ 00110 iofunc_func_init(_RESMGR_CONNECT_NFUNCS, &connect_funcs, 00111 _RESMGR_IO_NFUNCS, &io_funcs); 00112 00113 io_funcs.msg = subbus_io_msg; 00114 io_funcs.write = subbus_write; // For Quit only 00115 00116 /* initialize attribute structure used by the device */ 00117 iofunc_attr_init(&attr, S_IFNAM | 0666, 0, 0); 00118 00119 /* attach our device name */ 00120 id = resmgr_attach( 00121 dpp, /* dispatch handle */ 00122 &resmgr_attr, /* resource manager attrs */ 00123 DEVNAME, /* device name */ 00124 _FTYPE_ANY, /* open type */ 00125 0, /* flags */ 00126 &connect_funcs, /* connect routines */ 00127 &io_funcs, /* I/O routines */ 00128 &attr); /* handle */ 00129 if (id == -1) 00130 nl_error( 3, "%s: Unable to attach name.\n", argv[0]); 00131 init_subbus(dpp); 00132 nl_error( 0, "Initialized" ); 00133 00134 signal( SIGINT, sigint_handler ); 00135 signal( SIGHUP, sigint_handler ); 00136 00137 /* allocate a context structure */ 00138 ctp = dispatch_context_alloc(dpp); 00139 00140 /* start the resource manager message loop */ 00141 while (1) { 00142 if((ctp = dispatch_block(ctp)) == NULL) { 00143 if (errno == EINTR) break; 00144 nl_error( 3, "block error: %s", strerror(errno)); 00145 return EXIT_FAILURE; 00146 } 00147 dispatch_handler(ctp); 00148 if (SB_Shutdown == 1 && ctp->resmgr_context.rcvid == 0 00149 && attr.count == 0) 00150 break; 00151 } 00152 nl_error( 0, "Shutting down" ); 00153 shutdown_subbus(); 00154 return 0; 00155 } 00156