⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 geozone.c

📁 Open DMT Client C Source code
💻 C
📖 第 1 页 / 共 2 页
字号:
static CommandError_t _geozAddGeoZone(GeoZone_t *gz){#ifdef GEOZ_INCL_PRINT_GEOZONE    //_geozPrintGeoZone(gz);#endif    /* valid zone ID? */    if (!IS_VALID_ZONE(gz->zoneID)) { // NO_ZONE        // '0' is reserved for 'No GeoZone'        return COMMAND_ZONE_ID;    }    /* validate radius */    if (gz->radius <= 0) {        // the radius must be > 0        return COMMAND_RADIUS;    }    /* validate type */    GPSPoint_t pt0, pt1;    _geozToGPSPoint(&pt0, &(gz->point[0]));    _geozToGPSPoint(&pt1, &(gz->point[1]));#ifdef GEOF_DUAL_POINT_RADIUS    // Two separate points with the same specified radius    if (gz->type == GEOF_DUAL_POINT_RADIUS) {        if (!gpsPointIsValid(&pt0)) {            if (gpsPointIsValid(&pt1)) {                // move the valid point into point[0]                gz->point[0].latitude  = gz->point[1].latitude;                gz->point[0].longitude = gz->point[1].longitude;                gz->point[1].latitude  = 0.0;                gz->point[1].longitude = 0.0;            } else {                // at least one point must be valid                return COMMAND_LATLON;            }        }    } else#endif#ifdef GEOF_BOUNDED_RECT    // A simple rectangle bounded by an North-West point, and a South-East point    if (gz->type == GEOF_BOUNDED_RECT) {        // This GeoZone type will fail if the points spans the +/-180 deg meridian        if (!gpsPointIsValid(&pt0) || !gpsPointIsValid(&pt1)) {            // both points must be valid            return COMMAND_LATLON;        }        if (gz->point[0].latitude < gz->point[1].latitude) {            // move larger latitude to point[0]            float tmp = gz->point[0].latitude;            gz->point[0].latitude = gz->point[1].latitude;            gz->point[1].latitude = tmp;        }        if (gz->point[0].longitude > gz->point[1].longitude) {            // move smaller longitude to point[0]            float tmp = gz->point[0].longitude;            gz->point[0].longitude = gz->point[1].longitude;            gz->point[1].longitude = tmp;        }    } else#endif#ifdef GEOF_SWEPT_POINT_RADIUS    // A point radius swept over the globe from one point to another    if (gz->type == GEOF_SWEPT_POINT_RADIUS) {        if (!gpsPointIsValid(&pt0) || !gpsPointIsValid(&pt0)) {            // both points must be valid            return COMMAND_LATLON;        }        // The points should be a reasonable distance apart (ie. no more than a few miles)    } else#endif#ifdef GEOF_DELTA_RECT    // A center point with a +/- delta offset    if (gz->type == GEOF_DELTA_RECT) {        // This GeoZone type will fail if the points spans the +/-180 deg meridian        if (!gpsPointIsValid(&pt0)) {            // the center point must be valid            return COMMAND_LATLON;        }        if (gz->point[1].latitude == 0.0) {            // The delta latitude must be non zero            //gz->point[1].latitude = 0.0200;            return COMMAND_LATLON;        }        if (gz->point[1].longitude == 0.0) {            // The delta latitude must be non zero            //gz->point[1].longitude = 0.0200;            return COMMAND_LATLON;        }        if (gz->point[1].latitude < 0.0) {            // The delta latitude must be positive            gz->point[1].latitude = -gz->point[1].latitude;        }        if (gz->point[1].longitude < 0.0) {            // The delta latitude must be positive            gz->point[1].longitude = -gz->point[1].longitude;        }    } else#endif    {        // type not supported        return COMMAND_TYPE;    }        /* unique ZoneIDs? */#ifdef FORCE_UNIQUE_ZONE_IDS    _geozRemoveGeoZone(gz->zoneID);#endif    /* get available insert point */    UInt16 zoneNdx = 0;    for (zoneNdx = 0; zoneNdx < usedZones; zoneNdx++) {        if (!IS_VALID_ZONE(geoZoneList[zoneNdx].zoneID)) { // NO_ZONE            break;        }    }    if (zoneNdx >= maxZones) {        // we've reached the maximum limit        return COMMAND_OVERFLOW;    }    if (usedZones <= zoneNdx) {        // we're allocating another unused zone        usedZones = zoneNdx + 1;    }    /* add new geoZone */    memcpy(&geoZoneList[zoneNdx], gz, sizeof(GeoZone_t));    geozIsDirty = utTrue;    return COMMAND_OK;    }utBool geozAddGeoZone(GeoZone_t *gz){    if (gz) {        utBool addErr = utFalse;        GEOZ_LOCK {            addErr = (_geozAddGeoZone(gz) == COMMAND_OK)? utTrue : utFalse;        } GEOZ_UNLOCK        return addErr;    } else {        return utFalse;    }}// ----------------------------------------------------------------------------static utBool _geozRemoveGeoZone(GeoZoneID_t zoneID){    /* remove all GeoZones */    if (zoneID == NO_ZONE) {        if (usedZones != 0) {            usedZones = 0;            geozIsDirty = utTrue;            return utTrue;        } else {            return utFalse;        }    }        /* remove all matching geoZones */    utBool rtn = utFalse;    UInt16 i;    for (i = 0; i < usedZones; i++) {        if (zoneID == geoZoneList[i].zoneID) {            geoZoneList[i].zoneID = NO_ZONE;            geozIsDirty = utTrue;            rtn = utTrue;        }    }        /* trim back invalid zones at end of list */    for (; (usedZones > 0) && !IS_VALID_ZONE(geoZoneList[usedZones-1].zoneID); usedZones--);        /* clear current zone, if this zone was deleted */    GeoZoneID_t curZoneID = geozGetCurrentID();    if (zoneID == curZoneID) {        geozSetCurrentID(NO_ZONE);    }        return rtn;}utBool geozRemoveGeoZone(GeoZoneID_t zoneID){    utBool rmvErr = utFalse;    GEOZ_LOCK {        rmvErr = _geozRemoveGeoZone(zoneID);    } GEOZ_UNLOCK    return rmvErr;}// ----------------------------------------------------------------------------UInt16 geozGetGeoZoneCount(){    UInt16 i, count = 0;    for (i = 0; i < usedZones; i++) {        if (geoZoneList[i].zoneID != NO_ZONE) {            count++;        }    }    return count;}// ----------------------------------------------------------------------------static utBool _geozSaveGeoZones(const char *geozName){        /* invalid file name? */    if (!geozName || !*geozName) {        return utFalse;    }       /* file name */    char geozFile[256];    sprintf(geozFile, "%s", geozName);        /* open file for writing */    FILE *file = ioOpenStream(geozFile, IO_OPEN_WRITE);    if (!file) {        // error openning        logERROR(LOGSRC,"Unable to open GeoZone file for writing: %s", geozFile);        return utFalse;    }    /* write geozones to file */    UInt16 i = 0, count = 0;    for (i = 0; i < usedZones; i++) {        if (geoZoneList[i].zoneID != NO_ZONE) {            long wrtLen = ioWriteStream(file, (UInt8*)&geoZoneList[i], sizeof(GeoZone_t));            if (wrtLen < sizeof(GeoZone_t)) {                logERROR(LOGSRC,"Unable to write GeoZone: [%ld] %s", i, geozFile);                ioCloseStream(file);                return utFalse;            }            count++;        }    }        /* close file */    logINFO(LOGSRC,"Saved GeoZone file: %s [%u]", geozFile, count);    ioCloseStream(file);    geozIsDirty = utFalse;    return utTrue;}utBool geozSaveGeoZone(){    utBool savErr = utFalse;    GEOZ_LOCK {        savErr = _geozSaveGeoZones(GEOZONE_FILENAME);    } GEOZ_UNLOCK    return savErr;}// ----------------------------------------------------------------------------static utBool _geozLoadGeoZones(const char *geozName){        /* reset terminals */    _geozClearAll();    geozIsDirty = utFalse;    /* file name */    char geozFile[256];    sprintf(geozFile, "%s", geozName);        /* make sure file exists */    if (!ioIsFile(geozFile)) {        logINFO(LOGSRC,"GeoZone file does not exist: %s", geozFile);        return utFalse;    }    /* open file for writing */    FILE *file = ioOpenStream(geozFile, IO_OPEN_READ);    if (!file) {        // error openning        logERROR(LOGSRC,"Unable to open GeoZone file for reading: %s", geozFile);        return utFalse;    }        /* read terminals */    logINFO(LOGSRC,"Loading GeoZones: %s", geozFile);    usedZones = 0;    for (; usedZones < maxZones; usedZones++) {        GeoZone_t *geoz = &geoZoneList[usedZones];        /* read GeoZone record */        long vlen = ioReadStream(file, geoz, sizeof(GeoZone_t));        if (vlen < 0L) {            logERROR(LOGSRC,"Error reading GeoZone: [rcd=%u] %s", usedZones, geozFile);            ioCloseStream(file);            return utFalse; // error        } else        if (vlen == 0L) {            logINFO(LOGSRC,"Loaded GeoZones: [cnt=%u] %s", usedZones, geozFile);            ioCloseStream(file);            break;        } else        if (vlen < sizeof(GeoZone_t)) {            logERROR(LOGSRC,"Unable to read GeoZone: [rcd=%u] %s", usedZones, geozFile);            ioCloseStream(file);            return utFalse; // error        }#ifdef GEOZ_INCL_PRINT_GEOZONE        //_geozPrintGeoZone(geoz);#endif    }        return utTrue;}// ----------------------------------------------------------------------------// PROP_CMD_GEOF_ADMIN property handlerCommandError_t _cmdGeoZoneAdmin(int pi, Key_t key, const UInt8 *data, int dataLen){        /* init buffer */    Buffer_t bsrc, *src = binBuffer(&bsrc, (UInt8*)data, dataLen, BUFFER_SOURCE);    if (BUFFER_DATA_LENGTH(src) < 1) {        return COMMAND_ARGUMENTS;    }        /* admin command type */    Int32 adminType = -1L;    binBufScanf(src, "%1u", &adminType);    CommandError_t cmdErr = COMMAND_FEATURE_NOT_SUPPORTED;    switch ((Int16)adminType) {        case GEOF_CMD_ADD_STD:  // Add GeoZone list to table (standard resolution)        case GEOF_CMD_ADD_HIGH: // Add GeoZone list to table (high resolution)            cmdErr = COMMAND_OK;            GEOZ_LOCK {                utBool hiRes = ((Int16)adminType == GEOF_CMD_ADD_HIGH)? utTrue : utFalse;                while (BUFFER_DATA_LENGTH(src) >= PACKED_GEOZONE_SIZE) {                    GeoZone_t gz;                    if (_geozDecodeGeoZone(src, &gz, hiRes)) {                        CommandError_t addErr = _geozAddGeoZone(&gz);                        if (addErr != COMMAND_OK) {                            cmdErr = addErr;                        }                    } else {                        cmdErr = COMMAND_ARGUMENTS;                    }                }                if (BUFFER_DATA_LENGTH(src) > 0) {                    cmdErr = COMMAND_OVERFLOW;                }            } GEOZ_UNLOCK            break;        case GEOF_CMD_REMOVE: // Remove specified GeoZone(terminal) ID from table            cmdErr = COMMAND_OK;            GEOZ_LOCK {                if (BUFFER_DATA_LENGTH(src) == 0) {                    // this will remove ALL Geozones!                    _geozRemoveGeoZone((GeoZoneID_t)NO_ZONE);                } else {                    while (BUFFER_DATA_LENGTH(src) >= sizeof(GeoZoneID_t)) {                        UInt32 zoneID = 0L;                        binBufScanf(src, "%*x", sizeof(GeoZoneID_t), &zoneID);                        _geozRemoveGeoZone((GeoZoneID_t)zoneID);                    }                    if (BUFFER_DATA_LENGTH(src) > 0) {                        cmdErr = COMMAND_OVERFLOW;                    }                }            } GEOZ_UNLOCK            break;        case GEOF_CMD_SAVE: // Save GeoZone table to predefined location.            GEOZ_LOCK {                cmdErr = _geozSaveGeoZones(GEOZONE_FILENAME)?                    COMMAND_OK_ACK :    // COMMAND_OK;                    COMMAND_EXECUTION;  // not saved            } GEOZ_UNLOCK            break;        default:            cmdErr = COMMAND_FEATURE_NOT_SUPPORTED;            break;    }        /* return error */    return cmdErr;}// ----------------------------------------------------------------------------/* initialize geofence module */void geozInitialize(eventAddFtn_t queueEvent){        /* already initialized? */    if (didInitialize) {        return; // init only once    }    didInitialize = utTrue;     /* event generator */    ftnQueueEvent = queueEvent;            /* init lock */#ifdef ENABLE_THREADS    threadMutexInit(&geozMutex);#endif    /* init vars */    gpsClear(&arrivePoint);    gpsClear(&departPoint);    _geozLoadGeoZones(GEOZONE_FILENAME);            /* set geozone property command handler */    propSetCommandFtn(PROP_CMD_GEOF_ADMIN, &_cmdGeoZoneAdmin);        /* debug stuff */    //GeoZone_t _gz, *gz = &_gz;    //logDEBUG(LOGSRC,"sizeof(GeoZone_t)        = %d", sizeof(_gz));    //logDEBUG(LOGSRC,"sizeof(GeoZone_t.point)  = %d", sizeof(gz->point));    //logDEBUG(LOGSRC,"addr(&(GeoZone_t.point)) = %ld", (UInt32)((UInt32)&(gz->point) - (UInt32)gz));}// ----------------------------------------------------------------------------

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -