write-hdd

了解寫入HDD程序


更新記錄

item note
20170301 第一版
20170331 main flow , SManager_StreamAgentThd

目錄


main flow

[Main Flow]

SManager_StreamAgentThd

[SManager_StreamAgentThd]

Writer_RecordThd

  • Writer_RecordThd
    預先開啟,104個512K / 1000個150K大小buffer
    當buf裡有資料,就儲存到1M大小的暫存
    當資料大於1M大小則寫入硬碟
[Writer_RecordThd]

BKTREC_WriteVideoStream

  • BKTREC_WriteVideoStream
    將camera的video資料存於bkt中
    若為i-frame則更新rdb資料

  • 每分鐘執行一次memcpy rdb
    gBKTREC_Ctrl.idx_sect.t1[ch]:存儲bkt各CH第一次I-FRAME進來時間
    gBKTREC_Ctrl.idx_sect.t2[ch]:存儲bkt各CH每次I-FRAME進來時間

[BKTREC_WriteVideoStream]

BKTREC_FlushWriteBuffer

  • BKTREC_FlushWriteBuffer
    將目前的資料buf裡資料寫入檔案
    g_handle_rec_bkt目前開啟bkt檔案的fd
    gBKTREC_Ctrl.b_buf[1M] :存放當下資料(此資料尚未儲存於硬碟)
    gBKTREC_Ctr.pos : 記錄暫存buf使用量
[BKTREC_FlushWriteBuffer]

BKTREC_Flush_RDBDATA

  • BKTREC_Flush_RDBDATA
    1.先把/media/sda1/rdb/20170302的rdb檔案整個讀到evts及rdbs變數裡面
    1-1.更新相對應的時間內T_BASKET_RDB
    2.更新topmgr.udf裡面tm.reserved2時間
    1
    2
    3
    4
    5
    6
    7
    8
    #### BKTREC_Flush_RDBDATA
    BKTREC_Flush_RDBDATA /media/sda1/rdb/20170303
    [BKTREC] - update rdb.CNT: 3, UPDATED-CNT: 3, RBUF-POS:0 /media/sda1/rdb/20170303===============
    SAVE [/media/sda1/topmgr.udf] ok
    #### BKTREC_Flush_RDBDATA
    BKTREC_Flush_RDBDATA /media/sda1/rdb/20170303
    [BKTREC] - update rdb.CNT: 2, UPDATED-CNT: 2, RBUF-POS:0 /media/sda1/rdb/20170303===============
    SAVE [/media/sda1/topmgr.udf] ok
[BKTREC_FlushWriteBuffer]

BKTREC_SaveFull

  • BKTREC_SaveFull
    設定flag為SF_FULL
    關閉相關的bkt及idx的fd
    g_handle_rec_bkt : 目前使用的bkt fd
    g_hand_rec_idx : 目前使用的idx fd

  • bktmgr.udf
    {head,bid=0 body,bid=1 body,,,}
    儲存此硬碟所以bkt數量,及每個bkt flag

[BKTREC_SaveFull]

BKTREC_OpenFullBasket

  • BKTREC_OpenFullBasket
    尋找下一個bkt,必要時會換到下一個硬碟
    並且重新設定gBKTREC_Ctrl相關變數(bkt,idx)
    開啟時設定bktmgr.udf及bkt_rec_info.udf為SF_USING

  • 當bkt滿需要判斷是否要換硬碟
    由gBKTREC_Ctrl.bid及gBKTREC_Ctrl.bkt_cnt決定
    gBKTREC_Ctrl.bid:表示目前正在錄第幾個bkt
    gBKTREC_Ctrl.bkt_cnt:表示此硬碟最大的bkt數量

  • 若採用寫入最舊的日期
    可能遇到跳硬碟非預期的最大bkt數,當時間有被往後更動

[BKTREC_OpenFullBasket]

BKTREC_setTargetDisk

  • BKTREC_setTargetDisk
    設定gBKTREC_Ctrl到目前選到的硬碟及更新topmgr.udf時間
    取得bktmgr.udf裡面bkt_cnt資料 (表示此硬碟最大bkt cnt)
    gBKTREC_Ctrl.bkt_cnt:用判斷目前的bid是否為最大,若是則需要換下一個HDD

  • /mnt/nand/dvrap_cfg/hddmgr.udf
    記錄此硬碟
    curid: 目前是在第幾個idx
    hddcnt: 目前dvr系統,總共HDD量

  • /media/sda1/topmgr.udf
    記錄此硬碟,跟下一個及上一個串例
    當選到此硬碟時會更新時間(reserveded2)

[BKTREC_setTargetDisk]

BKTREC_searchBasket

  • BKTREC_searchBasket
    由目前硬碟裡找出,預計要使用的bkt
    先找看看是否有正在使用的bkt(即SF_USING)
    若沒有則找看看是否有空的bkt(即SF_EMPTY)
    最後才找最舊的已錄滿的bkt(即SF_FULL)
flag note udf file
SF_EMPTY 新的硬碟找空的bkt /media/sda1/bktmgr.udf
SF_FULL 繞寫時使用最舊的 /media/sda1/bktmgr.udf
SF_USING 表示正在使用的BKT /media/sda1/bkt_rec_info.udf

當BKTREC_OpenFullBasket時會設定bkt SF_USING,即第一次開啟bkt,表示正在使用
當BKTREC_SaveFull,設定bkt SF_FULL,表示此bkt已錄滿要換其它bkt

  • BKTREC_searchOldestBasket
    BKTREC_removeRDB(bid,ts)
    由目前的硬碟裡找出最舊的bkt,找到如下
    bid:為將要錄影的bkt id
    ts:為目前最舊的時間

  • BKTREC_removeRDB
    將會刪除比此時間(ts 20170302)還要舊的rdb檔案
    並且找出/media/sda1/rdb/20170302,將相對的bid位置清除為0

  • BKTREC_searchUsingBasket
    當無bkt_rec_info.udf
    則表示第一次錄資料,會設定 g_bkt_rec_space = BKT_SPACE_REMAIN(找空的bkt)

[BKTREC_searchBasket]

InitProfile

  • InitProfile
    第一次執行會執行InitProfile
    也會設定gbk_mount_info (get_disk_info)
[InitProfile]

DVR_GetDiskInfo

[DVR_GetDiskInfo]
  • DVR_GetDiskInfo
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    ================================== dev 0 
    dev: /dev/sdb1
    dir :
    model : WDC WD10JUCT-63CYNY0 state : 2
    type : GPT
    sz_total : 976762
    sz_avail : 0
    sz_used : 0
    rec used : 0
    ================================== dev 0
    hdparm: ioctl 0x304 failed: Inappropriate ioctl for device
    <LIB_GetHddModel> Model Name:[WDC WD10JUCT-63CYNY0]
    ================================== dev 1
    dev: /dev/sda1
    dir : /media/sda1
    model : WDC WD10JUCT-63CYNY0 state : 3
    type : ext4
    sz_total : 975956
    sz_avail : 49556
    sz_used : 877588
    rec used : 3
    ================================== dev 1
    hdparm: ioctl 0x304 failed: Inappropriate ioctl for device
    <LIB_GetHddModel> Model Name:[ST4000VM000-1F3168]
    ================================== dev 2
    dev: /dev/sdc1
    dir : /media/sdb1
    model : ST4000VM000-1F3168 state : 3
    type : ext4
    sz_total : 3905304
    sz_avail : 3709752
    sz_used : 228
    rec used : 1
    ================================== dev 2
    hdparm: ioctl 0x304 failed: Inappropriate ioctl for device
    <LIB_GetHddModel> Model Name:[WDC WD10JUCT-63CYNY0]
    ================================== dev 3
    dev: /dev/sdd1
    dir : /media/sdc1
    model : WDC WD10JUCT-63CYNY0 state : 3
    type : ext4
    sz_total : 975956
    sz_avail : 49548
    sz_used : 877596
    rec used : 2
    ================================== dev 3

BKTREC_getTargetDisk

  • BKTREC_getTargetDisk
    設定gbk_mount_info
    並且設定currHddIdx為系統中最新的硬碟(由topmgr.udf中last_update_t決定)
    即由上次錄的地方開始錄
[BKTREC_getTargetDisk]

BKTREC_updateHddInfo

  • BKTREC_updateHddInfo
    依實際況狀(/dev/sdx及 /proc/partions)
    更新 gbk_mount_info
    由WriterUpdateMountInfo->BKTREC_getTargetDisk時會執行

  • 何時需要設定gbk_mount_info
    1.第一次開機需要更新gbk_mount_info
    initProfile->DVR_GetDiskInfo->WriterUpdateMountInfo
    2.每30秒check hdd
    DVR_CheckHddDependency->WriterUpdateMountInfo
    3.格式化HDD之後
    DVR_FormatHDD->WriterUpdateMountInfo

[BKTREC_updateHddInfo]

getHddTotalSize

  • getHddTotalSize
    每10秒執行一次getHddTotalSize
    getHddTotalSize / LIB_BasketInfo / DVR_BasketInfo / BKTREC_TotalBasketInfo

  • BKTREC_TotalBasketInfo
    開機10秒會只會執行一次

[getHddTotalSize]

BKTREC_TotalBasketInfo

  • BKTREC_TotalBasketInfo
    設定BKTREC_Ctrl.bkt_cnt

  • 設定情況如下
    1.錄滿硬碟需要更換到其它顆 (BKTREC_OpenFullBasket)
    2.開新的bkt檔案 (BKTREC_open)
    3.開機第一次設定 (BKTREC_setTargetDisk)

[BKTREC_TotalBasketInfo]

bktmgr.udf

  • bktmgr.udf

    1
    2
    3
    4
    5
    6
    7
    8
    9
    typedef struct
    {
    long id; ///< header id
    long mgrid; ///< manager file numbering
    long date; ///< seconds since the Epoch
    long latest_update; ///< date of latest update
    long bkt_count; ///< basket count
    long reserved;
    } T_BKTMGR_HDR;
  • bkt_count
    0x594 = 1428

    [bktmgr]