歡迎來到Linux教程網
Linux教程網
Linux教程網
Linux教程網
您现在的位置: Linux教程網 >> UnixLinux >  >> Linux編程 >> Linux編程

基於Android 的GPS 移植

最近負責 Android 驅動的GPS部分,所謂Android驅動 我覺得可以說成是linux應用

之前發了一個圖描述了 Android GPS 架構

GPS芯片大多采用串口通信,所以只要CPU能夠提供一個UART 驅動, 那麼跟GPS芯片通信是沒有問題的,

但是現在很多GPS功能不是一個單獨的芯片,大部分都是一個芯片上有好幾種無線模塊 比如 Blletooth WiFi FM等

有時候 有些功能就會去復用一個UART,這樣在管理上就相對麻煩, 要將一個UART驅動, 模擬成一個HCI的接口而後才能使GPS功能(TI1281)


比較好的是我們的項目是單一的GPS chip 聽說apple也是用的這一款,不過人家拿的是全部的source code,而我們只有部分的code而沒有核心算法的code 很郁悶, 但是即便是只有部分code從裡邊還是可以學到很多的機制


對於android GPS驅動來說主要的工作是實現HAL層 計編譯生成一個叫做gps.***.so的動態庫的 代碼.
由app發出定位申請,此時會去啟動一個定位服務線程,此線程會調用到Location provider 服務在App Framwork中,在次會通過被native方法調用到JNI中,JNI獲得GpsInterface並傳給接口一個回調函數的實現。
GpsInterface就是由HAL層最主要實現

介紹下gps.h下得重要相關結構題定義
在android2.3中gps.h定義在/hardware/inclue/hardware下
主要的結構
1、相關宏定義:

  • 定位模式定義
    /** Requested operational mode for GPS operation. */
    typedef uint32_t GpsPositionMode;
    // IMPORTANT: Note that the following values must match
    // constants in GpsLocationProvider.java.
    /** Mode for running GPS standalone (no assistance). */
    #define GPS_POSITION_MODE_STANDALONE    0    //純GPS 使用衛星定位
    /** AGPS MS-Based mode. */
    #define GPS_POSITION_MODE_MS_BASED      1    //基於用戶終端的A-GPS
    /** AGPS MS-Assisted mode. */
    #define GPS_POSITION_MODE_MS_ASSISTED   2    //基於用戶終端輔助A-GPS



  • 工作模式
    /** Requested recurrence mode for GPS operation. */
    typedef uint32_t GpsPositionRecurrence;
    // IMPORTANT: Note that the following values must match
    // constants in GpsLocationProvider.java.
    /** Receive GPS fixes on a recurring basis at a specified period. */
    #define GPS_POSITION_RECURRENCE_PERIODIC    0//周期性的
    /** Request a single shot GPS fix. */
    #define GPS_POSITION_RECURRENCE_SINGLE      1//單次工作

  • 輔助數據(在測試GPS性能時候又是需要刪除全部或部分的輔助數據)
    /** Flags used to specify which aiding data to delete
        when calling delete_aiding_data(). */
    typedef uint16_t GpsAidingData;
    // IMPORTANT: Note that the following values must match
    // constants in GpsLocationProvider.java.
    #define GPS_DELETE_EPHEMERIS        0x0001
    #define GPS_DELETE_ALMANAC          0x0002
    #define GPS_DELETE_POSITION         0x0004
    #define GPS_DELETE_TIME             0x0008
    #define GPS_DELETE_IONO             0x0010
    #define GPS_DELETE_UTC              0x0020
    #define GPS_DELETE_HEALTH           0x0040
    #define GPS_DELETE_SVDIR            0x0080
    #define GPS_DELETE_SVSTEER          0x0100
    #define GPS_DELETE_SADATA           0x0200
    #define GPS_DELETE_RTI              0x0400
    #define GPS_DELETE_CELLDB_INFO      0x8000
    #define GPS_DELETE_ALL              0xFFFF
  • gps芯片可以處理的“能力”
    /** Flags for the gps_set_capabilities callback. */

    /** GPS HAL schedules fixes for GPS_POSITION_RECURRENCE_PERIODIC mode.
        If this is not set, then the framework will use 1000ms for min_interval
        and will start and call start() and stop() to schedule the GPS.
     */
    #define GPS_CAPABILITY_SCHEDULING       0x0000001/** GPS supports MS-Based AGPS mode */
    #define GPS_CAPABILITY_MSB              0x0000002/** GPS supports MS-Assisted AGPS mode */
    #define GPS_CAPABILITY_MSA              0x0000004/** GPS supports single-shot fixes */
    #define GPS_CAPABILITY_SINGLE_SHOT      0x0000008
  • 還有很多的定義此處不一一列舉 在gps.h中都有很好的解釋。

2、數據結構體

  • GpsLocation   
    定義了一個表示方位的結構體,成員有經緯度,高度,速度,方位角等。
  • GpsStatus
    表示GPS的當前狀態,只有兩個成員一個是表示結構大小的成員,與一個表示Gps狀態的類型GpsStatusValue
    /** GPS status event values. */
    typedef uint16_t GpsStatusValue;
    // IMPORTANT: Note that the following values must match
    // constants in GpsLocationProvider.java.
    /** GPS status unknown. */
    #define GPS_STATUS_NONE             0/** GPS has begun navigating. */
    #define GPS_STATUS_SESSION_BEGIN    1/** GPS has stopped navigating. */
    #define GPS_STATUS_SESSION_END      2/** GPS has powered on but is not navigating. */
    #define GPS_STATUS_ENGINE_ON        3/** GPS is powered off. */
    #define GPS_STATUS_ENGINE_OFF       4
  • GpsSvInfo
    表示當前的衛星信息,有衛星編號,信號強度,衛星仰望角方位角等
  • GpsSvStatus
    表示衛星狀態,包含了GpsSvInfo結構,可見衛星數,星歷時間,年歷時間,與用來定位的衛星的衛星構成的一個掩碼
  • AGpsRefLocation
    /* 2G and 3G */
    /* In 3G lac is discarded */
    typedef struct {
        uint16_t type;
        uint16_t mcc;
        uint16_t mnc;
        uint16_t lac;
        uint32_t cid;
    } AGpsRefLocationCellID;

    typedef struct {
        uint8_t mac[6];
    } AGpsRefLocationMac;

    /** Represents ref locations */
    typedef struct {
        uint16_t type;
        union {
            AGpsRefLocationCellID   cellID;
            AGpsRefLocationMac      mac;
        } u;
    } AGpsRefLocation;
    /** Represents the status of AGPS. */
    typedef struct {
        /** set to sizeof(AGpsStatus) */
        size_t          size;


        AGpsType        type;
        AGpsStatusValue status;
    } AGpsStatus

3、回調函數指針定義

/* Callback with location information. 告知上層位置信息*/
typedef void (* gps_location_callback)(GpsLocation* location);

/** Callback with status information.GPS狀態信息回調*/
typedef void (* gps_status_callback)(GpsStatus* status);

/** Callback with SV status information.衛星狀態信息回調 */
typedef void (* gps_sv_status_callback)(GpsSvStatus* sv_info);

/** Callback for reporting NMEA sentences. 向上層傳遞NEMA數據*/
typedef void (* gps_nmea_callback)(GpsUtcTime timestamp, const char* nmea, int length);

/** Callback to inform framework of the GPS engine's capabilities.告知上層次GPS能實現那些功能 */
typedef void (* gps_set_capabilities)(uint32_t capabilities);

/** Callback utility for acquiring the GPS wakelock.gps上鎖 讓gps功能不會被suspend*/
typedef void (* gps_acquire_wakelock)();

/** Callback utility for releasing the GPS wakelock. 釋放鎖*/
typedef void (* gps_release_wakelock)();

/** Callback for creating a thread that can call into the Java framework code.thread create 
在次線程處理函數中通常會由一個無限的循環,去等待上層的請求,並應答*/
typedef pthread_t (* gps_create_thread)(const char* name, void (*start)(void *), void* arg);

4、接口結構體

  • GpsCallbacks
    typedef struct {
        /** set to sizeof(GpsCallbacks) */
        size_t      size;
        gps_location_callback location_cb;
        gps_status_callback status_cb;
        gps_sv_status_callback sv_status_cb;
        gps_nmea_callback nmea_cb;
        gps_set_capabilities set_capabilities_cb;
        gps_acquire_wakelock acquire_wakelock_cb;
        gps_release_wakelock release_wakelock_cb;
        gps_create_thread create_thread_cb;
    } GpsCallbacks;
    就是以上函數指針組成的結構體,是一組回調函數,函數的實現在JNI層是Android實現好了得,無需做(太大的)修改

  • GpsInterface 
    Android GPS 最主要的數據結構,我們最主要的移植工作就是實現其中的函數
    /** Represents the standard GPS interface. */
    typedef struct {
        /** set to sizeof(GpsInterface) */
        size_t          size;
        /*Opens the interface and provides the callback routines 初始化callbacks 為JNI傳下來的 
       在此會使用callbacks中的create_thread_cb 來創建一個線程處理函數一直循環,等待任務處理*/
        int   (*init)( GpsCallbacks* callbacks );              

        /** Starts navigating. */
        int   (*start)( void );

        /** Stops navigating. */
        int   (*stop)( void );

        /** Closes the interface. */
        void  (*cleanup)( void );

        /** Injects the current time. 填入時間*/
        int   (*inject_time)(GpsUtcTime time, int64_t timeReference,
                             int uncertainty);

        /** Injects current location from another location provider 填入位置*/
        int  (*inject_location)(double latitude, double longitude, float accuracy);

        /*刪除全部or部分輔助數據 在性能測試時候使用*/
        void  (*delete_aiding_data)(GpsAidingData flags);

        /*設置定位模式 與GPS工作模式等等*/
        int   (*set_position_mode)(GpsPositionMode mode, GpsPositionRecurrence recurrence,
                uint32_t min_interval, uint32_t preferred_accuracy, uint32_t preferred_time);

        /*自行添加的 接口 AGpsInterface接口通過次函數獲得*/
        const void* (*get_extension)(const char* name);
    } GpsInterface;
  • AGpsCallbacks
    /** Callback with AGPS status information.
     *  Can only be called from a thread created by create_thread_cb.
     */
    typedef void (* agps_status_callback)(AGpsStatus* status);

    /** Callback structure for the AGPS interface. */
    typedef struct {
        agps_status_callback status_cb;
        gps_create_thread create_thread_cb;
    } AGpsCallbacks;
  • AGpsInterface
    /** Extended interface for AGPS support. */
    typedef struct {
        /** set to sizeof(AGpsInterface) */
        size_t          size;

        /**
         * Opens the AGPS interface and provides the callback routines
         * to the implemenation of this interface.
         */
        void  (*init)( AGpsCallbacks* callbacks );
        /**
         * Notifies that a data connection is available and sets 
         * the name of the APN to be used for SUPL.
         */
        int  (*data_conn_open)( const char* apn );
        /**
         * Notifies that the AGPS data connection has been closed.
         */
        int  (*data_conn_closed)();
        /**
         * Notifies that a data connection is not available for AGPS. 
         */
        int  (*data_conn_failed)();
        /**
         * Sets the hostname and port for the AGPS server.
         */
        int  (*set_server)( AGpsType type, const char* hostname, int port );
    } AGpsInterface
  • struct gps_device_t
    定義描述gps設備類型
    struct gps_device_t {
        struct hw_device_t common;

        /**
         * Set the provided lights to the provided values.
         *
         * Returns: 0 on succes, error code on failure.
         */
        const GpsInterface* (*get_gps_interface)(struct gps_device_t* dev);   
    };上層會通過動態庫,獲得此結構,等到GpsInterface從而打通APP到GPS device的全部通信。

  • 還有 GpsNiInterface AGpsRilInterface等接口 在此不贅述

Copyright © Linux教程網 All Rights Reserved