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 
00032 
00033 
00034 
00035 
00036 
00037 
00038 
00039 
00040 
00041 
00042 
00043 
00044 
00045 
00046 
00047 
00048 
00049 
00050 
00051 
00052 
00053 
00054 
00055 
00056 #include "biotac_sensors/cheetah.h"
00057 
00058 
00059 
00060 
00061 
00062 #define CH_CFILE_VERSION   0x0300   
00063 #define CH_REQ_SW_VERSION  0x0300   
00064 
00065 
00066 
00067 
00068 
00069 #ifndef CH_HEADER_VERSION
00070 #  error Unable to include header file. Please check include path.
00071 
00072 #elif CH_HEADER_VERSION != CH_CFILE_VERSION
00073 #  error Version mismatch between source and header files.
00074 
00075 #endif
00076 
00077 
00078 
00079 
00080 
00081 #define API_NAME                     "cheetah"
00082 #define API_DEBUG                    CH_DEBUG
00083 #define API_OK                       CH_OK
00084 #define API_UNABLE_TO_LOAD_LIBRARY   CH_UNABLE_TO_LOAD_LIBRARY
00085 #define API_INCOMPATIBLE_LIBRARY     CH_INCOMPATIBLE_LIBRARY
00086 #define API_UNABLE_TO_LOAD_FUNCTION  CH_UNABLE_TO_LOAD_FUNCTION
00087 #define API_HEADER_VERSION           CH_HEADER_VERSION
00088 #define API_REQ_SW_VERSION           CH_REQ_SW_VERSION
00089 
00090 
00091 
00092 
00093 
00094 #if defined(__APPLE_CC__) && !defined(DARWIN)
00095 #define DARWIN
00096 #endif
00097 
00098 #if defined(linux) || defined(DARWIN)
00099 
00100 #include <stdio.h>
00101 #include <stdlib.h>
00102 #include <unistd.h>
00103 #include <string.h>
00104 #include <fcntl.h>
00105 
00106 #ifdef DARWIN
00107 #define DLOPEN_NO_WARN
00108 extern int _NSGetExecutablePath (char *buf, unsigned long *bufsize);
00109 #endif
00110 
00111 #include <dlfcn.h>
00112 
00113 #define DLL_HANDLE  void *
00114 #define MAX_SO_PATH 256
00115 
00116 static char SO_NAME[MAX_SO_PATH+1] = API_NAME ".so";
00117 
00118 
00119 
00120 
00121 
00122 
00123 
00124 
00125 
00126 
00127 
00128 
00129 
00130 
00131 
00132 
00133 
00134 static int _checkPath (const char *path) {
00135     char *filename = (char *)malloc(strlen(path) +1 + strlen(SO_NAME) +1);
00136     int   fd;
00137 
00138     
00139     sprintf(filename, "%s/%s", path, SO_NAME);
00140     fd = open(filename, O_RDONLY);
00141     if (fd >= 0) {
00142         strncpy(SO_NAME, filename, MAX_SO_PATH);
00143         close(fd);
00144     }
00145 
00146     
00147     free(filename);
00148     return (fd >= 0);
00149 }
00150 
00151 static int _getExecPath (char *path, unsigned long maxlen) {
00152 #ifdef linux
00153     return readlink("/proc/self/exe", path, maxlen);
00154 #endif
00155 
00156 #ifdef DARWIN
00157     _NSGetExecutablePath(path, &maxlen);
00158     return maxlen;
00159 #endif
00160 }
00161 
00162 static void _setSearchPath () {
00163     char  path[MAX_SO_PATH+1];
00164     int   count;
00165     char *p;
00166 
00167     
00168     if (SO_NAME[0] == '/')  return;
00169 
00170     
00171     memset(path, 0, sizeof(path));
00172     count = _getExecPath(path, MAX_SO_PATH);
00173 
00174     if (count > 0) {
00175         char *p = strrchr(path, '/');
00176         if (p == path)  ++p;
00177         if (p != 0)     *p = '\0';
00178 
00179         
00180         if (_checkPath(path))  return;
00181     }
00182 
00183     
00184     p = getcwd(path, MAX_SO_PATH);
00185     if (p != 0)  _checkPath(path);
00186 }
00187 
00188 #endif
00189 
00190 
00191 
00192 
00193 
00194 #if defined(WIN32) || defined(_WIN32)
00195 
00196 #include <stdio.h>
00197 #include <windows.h>
00198 
00199 #define DLL_HANDLE           HINSTANCE
00200 #define dlopen(name, flags)  LoadLibraryA(name)
00201 #define dlsym(handle, name)  GetProcAddress(handle, name)
00202 #define dlerror()            "Exiting program"
00203 #define SO_NAME              API_NAME ".dll"
00204 
00205 
00206 
00207 
00208 
00209 
00210 
00211 
00212 
00213 
00214 
00215 
00216 
00217 static void _setSearchPath () {
00218     
00219 }
00220 
00221 #endif
00222 
00223 
00224 
00225 
00226 
00227 
00228 static void *_loadFunction (const char *name, int *result) {
00229     static DLL_HANDLE handle = 0;
00230     void * function = 0;
00231 
00232     
00233     if (handle == 0) {
00234         u32 (*version) (void);
00235         u16 sw_version;
00236         u16 api_version_req;
00237 
00238         _setSearchPath();
00239         handle = dlopen(SO_NAME, RTLD_LAZY);
00240         if (handle == 0) {
00241 #if API_DEBUG
00242             fprintf(stderr, "Unable to load %s\n", SO_NAME);
00243             fprintf(stderr, "%s\n", dlerror());
00244 #endif
00245             *result = API_UNABLE_TO_LOAD_LIBRARY;
00246             return 0;
00247         }
00248 
00249         version = (void *)dlsym(handle, "c_version");
00250         if (version == 0) {
00251 #if API_DEBUG
00252             fprintf(stderr, "Unable to bind c_version() in %s\n",
00253                     SO_NAME);
00254             fprintf(stderr, "%s\n", dlerror());
00255 #endif
00256             handle  = 0;
00257             *result = API_INCOMPATIBLE_LIBRARY;
00258             return 0;
00259         }
00260 
00261         sw_version      = (u16)((version() >>  0) & 0xffff);
00262         api_version_req = (u16)((version() >> 16) & 0xffff);
00263         if (sw_version  < API_REQ_SW_VERSION ||
00264             API_HEADER_VERSION < api_version_req)
00265         {
00266 #if API_DEBUG
00267             fprintf(stderr, "\nIncompatible versions:\n");
00268 
00269             fprintf(stderr, "  Header version  = v%d.%02d  ",
00270                     (API_HEADER_VERSION >> 8) & 0xff, API_HEADER_VERSION & 0xff);
00271 
00272             if (sw_version < API_REQ_SW_VERSION)
00273                 fprintf(stderr, "(requires library >= %d.%02d)\n",
00274                         (API_REQ_SW_VERSION >> 8) & 0xff,
00275                         API_REQ_SW_VERSION & 0xff);
00276             else
00277                 fprintf(stderr, "(library version OK)\n");
00278                         
00279                    
00280             fprintf(stderr, "  Library version = v%d.%02d  ",
00281                     (sw_version >> 8) & 0xff,
00282                     (sw_version >> 0) & 0xff);
00283 
00284             if (API_HEADER_VERSION < api_version_req)
00285                 fprintf(stderr, "(requires header >= %d.%02d)\n",
00286                         (api_version_req >> 8) & 0xff,
00287                         (api_version_req >> 0) & 0xff);
00288             else
00289                 fprintf(stderr, "(header version OK)\n");
00290 #endif
00291             handle  = 0;
00292             *result = API_INCOMPATIBLE_LIBRARY;
00293             return 0;
00294         }
00295     }
00296 
00297     
00298     function = (void *)dlsym(handle, name);
00299     *result  = function ? API_OK : API_UNABLE_TO_LOAD_FUNCTION;
00300     return function;
00301 }
00302 
00303 
00304 
00305 
00306 
00307 static int (*c_ch_find_devices) (int, u16 *) = 0;
00308 int ch_find_devices (
00309     int   num_devices,
00310     u16 * devices
00311 )
00312 {
00313     if (c_ch_find_devices == 0) {
00314         int res = 0;
00315         if (!(c_ch_find_devices = _loadFunction("c_ch_find_devices", &res)))
00316             return res;
00317     }
00318     return c_ch_find_devices(num_devices, devices);
00319 }
00320 
00321 
00322 static int (*c_ch_find_devices_ext) (int, u16 *, int, u32 *) = 0;
00323 int ch_find_devices_ext (
00324     int   num_devices,
00325     u16 * devices,
00326     int   num_ids,
00327     u32 * unique_ids
00328 )
00329 {
00330     if (c_ch_find_devices_ext == 0) {
00331         int res = 0;
00332         if (!(c_ch_find_devices_ext = _loadFunction("c_ch_find_devices_ext", &res)))
00333             return res;
00334     }
00335     return c_ch_find_devices_ext(num_devices, devices, num_ids, unique_ids);
00336 }
00337 
00338 
00339 static Cheetah (*c_ch_open) (int) = 0;
00340 Cheetah ch_open (
00341     int port_number
00342 )
00343 {
00344     if (c_ch_open == 0) {
00345         int res = 0;
00346         if (!(c_ch_open = _loadFunction("c_ch_open", &res)))
00347             return res;
00348     }
00349     return c_ch_open(port_number);
00350 }
00351 
00352 
00353 static Cheetah (*c_ch_open_ext) (int, CheetahExt *) = 0;
00354 Cheetah ch_open_ext (
00355     int          port_number,
00356     CheetahExt * ch_ext
00357 )
00358 {
00359     if (c_ch_open_ext == 0) {
00360         int res = 0;
00361         if (!(c_ch_open_ext = _loadFunction("c_ch_open_ext", &res)))
00362             return res;
00363     }
00364     return c_ch_open_ext(port_number, ch_ext);
00365 }
00366 
00367 
00368 static int (*c_ch_close) (Cheetah) = 0;
00369 int ch_close (
00370     Cheetah cheetah
00371 )
00372 {
00373     if (c_ch_close == 0) {
00374         int res = 0;
00375         if (!(c_ch_close = _loadFunction("c_ch_close", &res)))
00376             return res;
00377     }
00378     return c_ch_close(cheetah);
00379 }
00380 
00381 
00382 static int (*c_ch_port) (Cheetah) = 0;
00383 int ch_port (
00384     Cheetah cheetah
00385 )
00386 {
00387     if (c_ch_port == 0) {
00388         int res = 0;
00389         if (!(c_ch_port = _loadFunction("c_ch_port", &res)))
00390             return res;
00391     }
00392     return c_ch_port(cheetah);
00393 }
00394 
00395 
00396 static u32 (*c_ch_unique_id) (Cheetah) = 0;
00397 u32 ch_unique_id (
00398     Cheetah cheetah
00399 )
00400 {
00401     if (c_ch_unique_id == 0) {
00402         int res = 0;
00403         if (!(c_ch_unique_id = _loadFunction("c_ch_unique_id", &res)))
00404             return res;
00405     }
00406     return c_ch_unique_id(cheetah);
00407 }
00408 
00409 
00410 static const char * (*c_ch_status_string) (int) = 0;
00411 const char * ch_status_string (
00412     int status
00413 )
00414 {
00415     if (c_ch_status_string == 0) {
00416         int res = 0;
00417         if (!(c_ch_status_string = _loadFunction("c_ch_status_string", &res)))
00418             return 0;
00419     }
00420     return c_ch_status_string(status);
00421 }
00422 
00423 
00424 static int (*c_ch_version) (Cheetah, CheetahVersion *) = 0;
00425 int ch_version (
00426     Cheetah          cheetah,
00427     CheetahVersion * version
00428 )
00429 {
00430     if (c_ch_version == 0) {
00431         int res = 0;
00432         if (!(c_ch_version = _loadFunction("c_ch_version", &res)))
00433             return res;
00434     }
00435     return c_ch_version(cheetah, version);
00436 }
00437 
00438 
00439 static u32 (*c_ch_sleep_ms) (u32) = 0;
00440 u32 ch_sleep_ms (
00441     u32 milliseconds
00442 )
00443 {
00444     if (c_ch_sleep_ms == 0) {
00445         int res = 0;
00446         if (!(c_ch_sleep_ms = _loadFunction("c_ch_sleep_ms", &res)))
00447             return res;
00448     }
00449     return c_ch_sleep_ms(milliseconds);
00450 }
00451 
00452 
00453 static int (*c_ch_target_power) (Cheetah, u08) = 0;
00454 int ch_target_power (
00455     Cheetah cheetah,
00456     u08     power_flag
00457 )
00458 {
00459     if (c_ch_target_power == 0) {
00460         int res = 0;
00461         if (!(c_ch_target_power = _loadFunction("c_ch_target_power", &res)))
00462             return res;
00463     }
00464     return c_ch_target_power(cheetah, power_flag);
00465 }
00466 
00467 
00468 static int (*c_ch_host_ifce_speed) (Cheetah) = 0;
00469 int ch_host_ifce_speed (
00470     Cheetah cheetah
00471 )
00472 {
00473     if (c_ch_host_ifce_speed == 0) {
00474         int res = 0;
00475         if (!(c_ch_host_ifce_speed = _loadFunction("c_ch_host_ifce_speed", &res)))
00476             return res;
00477     }
00478     return c_ch_host_ifce_speed(cheetah);
00479 }
00480 
00481 
00482 static int (*c_ch_dev_addr) (Cheetah) = 0;
00483 int ch_dev_addr (
00484     Cheetah cheetah
00485 )
00486 {
00487     if (c_ch_dev_addr == 0) {
00488         int res = 0;
00489         if (!(c_ch_dev_addr = _loadFunction("c_ch_dev_addr", &res)))
00490             return res;
00491     }
00492     return c_ch_dev_addr(cheetah);
00493 }
00494 
00495 
00496 static int (*c_ch_spi_bitrate) (Cheetah, int) = 0;
00497 int ch_spi_bitrate (
00498     Cheetah cheetah,
00499     int     bitrate_khz
00500 )
00501 {
00502     if (c_ch_spi_bitrate == 0) {
00503         int res = 0;
00504         if (!(c_ch_spi_bitrate = _loadFunction("c_ch_spi_bitrate", &res)))
00505             return res;
00506     }
00507     return c_ch_spi_bitrate(cheetah, bitrate_khz);
00508 }
00509 
00510 
00511 static int (*c_ch_spi_configure) (Cheetah, CheetahSpiPolarity, CheetahSpiPhase, CheetahSpiBitorder, u08) = 0;
00512 int ch_spi_configure (
00513     Cheetah            cheetah,
00514     CheetahSpiPolarity polarity,
00515     CheetahSpiPhase    phase,
00516     CheetahSpiBitorder bitorder,
00517     u08                ss_polarity
00518 )
00519 {
00520     if (c_ch_spi_configure == 0) {
00521         int res = 0;
00522         if (!(c_ch_spi_configure = _loadFunction("c_ch_spi_configure", &res)))
00523             return res;
00524     }
00525     return c_ch_spi_configure(cheetah, polarity, phase, bitorder, ss_polarity);
00526 }
00527 
00528 
00529 static int (*c_ch_spi_queue_clear) (Cheetah) = 0;
00530 int ch_spi_queue_clear (
00531     Cheetah cheetah
00532 )
00533 {
00534     if (c_ch_spi_queue_clear == 0) {
00535         int res = 0;
00536         if (!(c_ch_spi_queue_clear = _loadFunction("c_ch_spi_queue_clear", &res)))
00537             return res;
00538     }
00539     return c_ch_spi_queue_clear(cheetah);
00540 }
00541 
00542 
00543 static int (*c_ch_spi_queue_oe) (Cheetah, u08) = 0;
00544 int ch_spi_queue_oe (
00545     Cheetah cheetah,
00546     u08     oe
00547 )
00548 {
00549     if (c_ch_spi_queue_oe == 0) {
00550         int res = 0;
00551         if (!(c_ch_spi_queue_oe = _loadFunction("c_ch_spi_queue_oe", &res)))
00552             return res;
00553     }
00554     return c_ch_spi_queue_oe(cheetah, oe);
00555 }
00556 
00557 
00558 static int (*c_ch_spi_queue_delay_cycles) (Cheetah, int) = 0;
00559 int ch_spi_queue_delay_cycles (
00560     Cheetah cheetah,
00561     int     cycles
00562 )
00563 {
00564     if (c_ch_spi_queue_delay_cycles == 0) {
00565         int res = 0;
00566         if (!(c_ch_spi_queue_delay_cycles = _loadFunction("c_ch_spi_queue_delay_cycles", &res)))
00567             return res;
00568     }
00569     return c_ch_spi_queue_delay_cycles(cheetah, cycles);
00570 }
00571 
00572 
00573 static int (*c_ch_spi_queue_delay_ns) (Cheetah, int) = 0;
00574 int ch_spi_queue_delay_ns (
00575     Cheetah cheetah,
00576     int     nanoseconds
00577 )
00578 {
00579     if (c_ch_spi_queue_delay_ns == 0) {
00580         int res = 0;
00581         if (!(c_ch_spi_queue_delay_ns = _loadFunction("c_ch_spi_queue_delay_ns", &res)))
00582             return res;
00583     }
00584     return c_ch_spi_queue_delay_ns(cheetah, nanoseconds);
00585 }
00586 
00587 
00588 static int (*c_ch_spi_queue_ss) (Cheetah, u08) = 0;
00589 int ch_spi_queue_ss (
00590     Cheetah cheetah,
00591     u08     active
00592 )
00593 {
00594     if (c_ch_spi_queue_ss == 0) {
00595         int res = 0;
00596         if (!(c_ch_spi_queue_ss = _loadFunction("c_ch_spi_queue_ss", &res)))
00597             return res;
00598     }
00599     return c_ch_spi_queue_ss(cheetah, active);
00600 }
00601 
00602 
00603 static int (*c_ch_spi_queue_byte) (Cheetah, int, u08) = 0;
00604 int ch_spi_queue_byte (
00605     Cheetah cheetah,
00606     int     count,
00607     u08     data
00608 )
00609 {
00610     if (c_ch_spi_queue_byte == 0) {
00611         int res = 0;
00612         if (!(c_ch_spi_queue_byte = _loadFunction("c_ch_spi_queue_byte", &res)))
00613             return res;
00614     }
00615     return c_ch_spi_queue_byte(cheetah, count, data);
00616 }
00617 
00618 
00619 static int (*c_ch_spi_queue_array) (Cheetah, int, const u08 *) = 0;
00620 int ch_spi_queue_array (
00621     Cheetah     cheetah,
00622     int         num_bytes,
00623     const u08 * data_out
00624 )
00625 {
00626     if (c_ch_spi_queue_array == 0) {
00627         int res = 0;
00628         if (!(c_ch_spi_queue_array = _loadFunction("c_ch_spi_queue_array", &res)))
00629             return res;
00630     }
00631     return c_ch_spi_queue_array(cheetah, num_bytes, data_out);
00632 }
00633 
00634 
00635 static int (*c_ch_spi_batch_length) (Cheetah) = 0;
00636 int ch_spi_batch_length (
00637     Cheetah cheetah
00638 )
00639 {
00640     if (c_ch_spi_batch_length == 0) {
00641         int res = 0;
00642         if (!(c_ch_spi_batch_length = _loadFunction("c_ch_spi_batch_length", &res)))
00643             return res;
00644     }
00645     return c_ch_spi_batch_length(cheetah);
00646 }
00647 
00648 
00649 static int (*c_ch_spi_batch_shift) (Cheetah, int, u08 *) = 0;
00650 int ch_spi_batch_shift (
00651     Cheetah cheetah,
00652     int     num_bytes,
00653     u08 *   data_in
00654 )
00655 {
00656     if (c_ch_spi_batch_shift == 0) {
00657         int res = 0;
00658         if (!(c_ch_spi_batch_shift = _loadFunction("c_ch_spi_batch_shift", &res)))
00659             return res;
00660     }
00661     return c_ch_spi_batch_shift(cheetah, num_bytes, data_in);
00662 }
00663 
00664 
00665 static int (*c_ch_spi_async_submit) (Cheetah) = 0;
00666 int ch_spi_async_submit (
00667     Cheetah cheetah
00668 )
00669 {
00670     if (c_ch_spi_async_submit == 0) {
00671         int res = 0;
00672         if (!(c_ch_spi_async_submit = _loadFunction("c_ch_spi_async_submit", &res)))
00673             return res;
00674     }
00675     return c_ch_spi_async_submit(cheetah);
00676 }
00677 
00678 
00679 static int (*c_ch_spi_async_collect) (Cheetah, int, u08 *) = 0;
00680 int ch_spi_async_collect (
00681     Cheetah cheetah,
00682     int     num_bytes,
00683     u08 *   data_in
00684 )
00685 {
00686     if (c_ch_spi_async_collect == 0) {
00687         int res = 0;
00688         if (!(c_ch_spi_async_collect = _loadFunction("c_ch_spi_async_collect", &res)))
00689             return res;
00690     }
00691     return c_ch_spi_async_collect(cheetah, num_bytes, data_in);
00692 }
00693 
00694