Import Humax upgrade support code
Build as libhmxupgrade.a
Humax provided no version number or tracking information. For future updates, we get to diff the files.
Change-Id: I6f82552a56c9e420a458c580b4097f4f8a5f5a57
diff --git a/libupgrade/Makefile b/libupgrade/Makefile
new file mode 100644
index 0000000..bcd0643
--- /dev/null
+++ b/libupgrade/Makefile
@@ -0,0 +1,28 @@
+# Copyright 2011 Google Inc. All Rights Reserved.
+# Author: dgentry@google.com (Denton Gentry)
+
+CROSS_PREFIX:=$(TARGET)
+CC:=$(CROSS_PREFIX)gcc
+CPP:=$(CROSS_PREFIX)g++
+LD:=$(CROSS_PREFIX)ld
+AR:=$(CROSS_PREFIX)ar
+RANLIB:=$(CROSS_PREFIX)ranlib
+STRIP:=$(CROSS_PREFIX)strip
+
+CFLAGS = -g -Os
+
+# util.c includes htype.h, which we don't have. Skip it, we don't need it right now.
+SRCS = hmx_upgrade.c hmx_upgrade_flash.c hmx_upgrade_nvram.c hmx_upgrade_system.c lib_queue.c
+INCS = hmx_upgrade.h hmx_upgrade_flash.h hmx_upgrade_nvram.h hmx_upgrade_system.h lib_queue.h util.h
+OBJS = $(SRCS:.c=.o)
+
+all: libupgrade.a
+
+.c.o:
+ $(CC) $(CFLAGS) -c $< -o $@
+
+libupgrade.a: $(OBJS) $(INCS)
+ $(AR) rcs $@ $(OBJS)
+
+clean:
+ rm -f libupgrade.a *.o
diff --git a/libupgrade/hmx_upgrade.c b/libupgrade/hmx_upgrade.c
new file mode 100644
index 0000000..a2ee417
--- /dev/null
+++ b/libupgrade/hmx_upgrade.c
@@ -0,0 +1,334 @@
+/*******************************************************************/
+/************************* File Description ************************/
+/*******************************************************************/
+/* File Name: $Workfile: hmx_uprade.c $
+ * Version: $Revision: 1.0 $
+ * Original Author: Yang Hyun Uk $
+ * Current Author: $Author: huyang@humaxdigital.com $
+ * Date: $Date: 2011.09.30
+ * File Description: HTTP Live Streaming
+ * Module:
+ * Remarks:
+ */
+
+/**
+ *
+ * @defgroup UPGRADE Upgrade APIs
+ *
+ */
+
+/**
+ * @author Hyunuk Yang(huyang@humaxdigital.com)
+ * @date 30 Sept 2011
+ */
+
+/**
+ * @note
+ * Copyright (C) 2011 Humax Corporation. All Rights Reserved. <br>
+ * This software is the confidential and proprietary information
+ * of Humax Corporation. You may not use or distribute this software
+ * except in compliance with the terms and conditions of any applicable license
+ * agreement in writing between Humax Corporation and you.
+ */
+
+ /*@{*/
+
+/**
+ * @file hmx_upgrade.c
+ */
+
+/*******************************************************************/
+/**************************** Header Files *************************/
+/*******************************************************************/
+/* Start Including Header Files */
+#include <stdio.h>
+#include "hmx_upgrade.h"
+#include "util.h"
+/* End Including Headers */
+
+
+/*******************************************************************/
+/****************************** define *****************************/
+/*******************************************************************/
+#define HMX_UPGRADE_NUMBER_OF_QUEUE 64
+#define HMX_UPGRADE_TASK_PRIORITY 10
+#define HMX_UPGRADE_TASK_STACK_SIZE (1024*128)
+
+/* End #define */
+
+/*******************************************************************/
+/****************************** typedef ****************************/
+/*******************************************************************/
+/* Start typedef */
+/* End typedef */
+
+
+/*******************************************************************/
+/************************ global variables *************************/
+/*******************************************************************/
+/* Start global variable */
+
+/**
+ * Upgrade Status Callback notifies status to APP
+ */
+HMX_UpgradeEventCallback g_fUpgradeStatusCallback = NULL;
+HMX_UPGRADE_COMMAND_t g_tUpgradeCommand;
+/* End global variable */
+
+
+/*******************************************************************/
+/************************ static variables *************************/
+/*******************************************************************/
+/* Start static variable */
+static unsigned long s_ulUpgradeTaskId = 0;
+static unsigned long s_ulUpgradeMessgseId=0;
+/* End static variable */
+
+static void P_HMX_Upgrade_Task(void* param);
+
+
+/**
+ * @b Function @b Description <br>
+ * Start Humax Upgrade Module. it creates a thread for Upgrading. <br>
+ *
+ * @param[in] callback : specify a callback to get Upgrade Status. if NULL, Upgrade Module can't be started.
+ * @param[in] file : specify a file path. also http address will be possible. if NULL, Upgrade Module can't be started.
+ *
+ * @return # 0 : success <br>
+ * # 1 : failed <br>
+ *
+ */
+int HMX_UPGRADE_Start( HMX_UpgradeEventCallback callback, unsigned char * file)
+{
+ int err;
+ HMX_UPGRADE_COMMAND_t upgrade_msg;
+
+ /* Add Callback */
+ if( callback == NULL )
+ {
+ printf("[%s] ERROR callback porinter is NULL \n", __FUNCTION__);
+ return 1;
+ }
+ g_fUpgradeStatusCallback = callback;
+
+ if ( file == NULL )
+ {
+ printf("[%s] ERROR file path is nULL\n", __FUNCTION__);
+ return 1;
+ }
+
+ err = HMX_MSG_Create(HMX_UPGRADE_NUMBER_OF_QUEUE, sizeof(HMX_UPGRADE_COMMAND_t), "UpgradeMsgQ", &s_ulUpgradeMessgseId, HMX_SUSPENDTYPE_FIFO);
+ if(err != HMX_OK)
+ {
+ printf("[%s] [%d] Error(0x%x) \n\r",__FUNCTION__,__LINE__, err);
+ return HMX_ERROR;
+ }
+
+ err = HMX_TASK_Create( P_HMX_Upgrade_Task, HMX_UPGRADE_TASK_PRIORITY, HMX_UPGRADE_TASK_STACK_SIZE, "UpgradeTask", NULL, &s_ulUpgradeTaskId, 0);
+ if( err != HMX_OK )
+ {
+ printf("[%s] [%d] Error(0x%x) \n\r",__FUNCTION__,__LINE__, err);
+ return HMX_ERROR;
+ }
+
+ HMX_TASK_Start(s_ulUpgradeTaskId);
+
+ upgrade_msg.command = HMX_UPGRADE_FETCH;
+ /* this should be freed at Reciever */
+ upgrade_msg.file_path = strdup(file);
+
+ err = HMX_MSG_Send(s_ulUpgradeMessgseId, &upgrade_msg, sizeof(HMX_UPGRADE_COMMAND_t),0);
+ if(err != HMX_OK)
+ {
+ printf( "[HMX_UPGRADE_Start] HMX_MSG_Send error : err is 0x%x\n", err);
+ return HMX_ERROR;
+ }
+
+ return HMX_OK;
+}
+
+/**
+ * @b Function @b Description <br>
+ * Stop Humax Upgrade Module. even it can be stoped while it is Reading or Flashing. <br>
+ *
+ * @return # 0 : success <br>
+ * # 1 : failed <br>
+ *
+ */
+int HMX_UPGRADE_Stop(void)
+{
+ int err;
+ HMX_UPGRADE_COMMAND_t upgrade_msg;
+ upgrade_msg.command = HMX_UPGRADE_STOP;
+
+ err = HMX_MSG_SendUrgent(s_ulUpgradeMessgseId, &upgrade_msg, sizeof(HMX_UPGRADE_COMMAND_t),0);
+ if(err != HMX_OK)
+ {
+ printf( "[HMX_UPGRADE_Stop] HMX_MSG_Send error : err is 0x%x\n", err);
+ return HMX_ERROR;
+ }
+
+ HMX_TASK_Stop(s_ulUpgradeTaskId);
+
+ err = HMX_TASK_Destroy(s_ulUpgradeTaskId);
+ if( err != HMX_OK )
+ {
+ printf("[%s] [%d] Error(0x%x) \n\r",__FUNCTION__,__LINE__, err);
+ return HMX_ERROR;
+ }
+
+ err = HMX_MSG_Destroy(s_ulUpgradeMessgseId);
+ if(err != HMX_OK)
+ {
+ printf("[%s] [%d] Error(0x%x) \n\r",__FUNCTION__,__LINE__, err);
+ return HMX_ERROR;
+ }
+
+ return HMX_OK;
+}
+
+#if 0
+/**
+ * @b Function @b Description <br>
+ * Specify a file to upgrade <br>
+ *
+ * @param[in] file : specify full file path.
+ *
+ * @return # 0 : success <br>
+ * # 1 : failed <br>
+ *
+ */
+int HMX_UPGRADE_FetchFileToUpgrade(unsigned char * file)
+{
+ int nErr;
+ HMX_UPGRADE_COMMAND_t upgrade_msg;
+
+ if ( file == NULL )
+ {
+ printf("[%s] file path is nULL\n", __FUNCTION__);
+ }
+
+ upgrade_msg.command = HMX_UPGRADE_FETCH;
+ /* this should be freed at Reciever */
+ upgrade_msg.file_path = strdup(file);
+
+ printf("[%s] file path is %s\n", __FUNCTION__, upgrade_msg.file_path);
+
+
+ nErr = HMX_MSG_SendTimeout(s_ulUpgradeMessgseId, &upgrade_msg, sizeof(HMX_UPGRADE_COMMAND_t),0);
+ if(nErr != HMX_OK)
+ {
+ printf( "[HMX_UPGRADE_FetchFileToUpgrade] HMX_MSG_Send error : err is 0x%x\n", nErr);
+ return HMX_ERR;
+ }
+
+ return HMX_OK;
+}
+#endif
+
+void HMX_UPGRADE_Call_Callback(HMX_UPGRADE_STATUS_Msg_t * upgrade_status_msg )
+{
+ if ( g_fUpgradeStatusCallback != NULL )
+ {
+ g_fUpgradeStatusCallback(upgrade_status_msg);
+ }
+
+}
+
+/*******************************************************************/
+/************************ static funtions **************************/
+/*******************************************************************/
+
+static HMX_UPGRADE_EVENT_e P_HMX_UPGRADE_FILE(unsigned char * path)
+{
+ HMX_UPGRADE_STATUS_Msg_t * upgrade_status_msg;
+ int ret;
+ upgrade_status_msg = malloc(sizeof(HMX_UPGRADE_STATUS_Msg_t));
+
+ printf ("[%s] \n", __FUNCTION__ );
+
+
+ ret = HMX_UPGRADE_HDF_Do_Flash( path );
+ if ( ret != HMX_OK )
+ {
+ printf ("[%s] HMX_UPGRADE_HDF_Do_Flash ret %d\n", __FUNCTION__, ret );
+ upgrade_status_msg->event = ret;
+ HMX_UPGRADE_Call_Callback(upgrade_status_msg);
+ return HMX_UPGRADE_FILE_NOT_EXIST;
+ }
+
+ free(upgrade_status_msg);
+ return HMX_UPGRADE_DONE;
+}
+
+static void P_HMX_Upgrade_Task(void* param)
+{
+ HMX_UPGRADE_EVENT_e nErr;
+ int upgrade_is_done = 0;
+ HMX_UPGRADE_COMMAND_t recieved_command;
+ unsigned char * file_path=NULL;
+ HMX_UPGRADE_COMMAND_t send_command;
+
+ HMX_UPGRADE_STATUS_Msg_t * upgrade_status_msg;
+ upgrade_status_msg = malloc(sizeof(upgrade_status_msg));
+
+ while(1)
+ {
+ nErr = HMX_MSG_Receive(s_ulUpgradeMessgseId, &recieved_command, sizeof(HMX_UPGRADE_COMMAND_t));
+ if(nErr != HMX_OK)
+ {
+ printf ("%s (%d) Error> Error VK_MSG_ReceiveTimeout\n",__FUNCTION__,__LINE__);
+ }
+ else
+ {
+ switch( recieved_command.command)
+ {
+ case HMX_UPGRADE_START:
+ {
+ printf("[%s] Receive HMX_UPGRADE_START command \n",__FUNCTION__);
+
+ /* DO Upgrade ........ here */
+ nErr = P_HMX_UPGRADE_FILE(file_path);
+
+ send_command.command = HMX_UPGRADE_STOP;
+ (void)HMX_MSG_Send(s_ulUpgradeMessgseId, &send_command, sizeof(HMX_UPGRADE_COMMAND_t),0);
+ break;
+ }
+ case HMX_UPGRADE_STOP:
+ {
+ printf("[%s] HMX_UPGRADE_STOP \r\n",__FUNCTION__);
+
+ free(upgrade_status_msg);
+ free(file_path);
+
+ /* Notify to app, UPgreade is done. */
+ upgrade_status_msg->event = HMX_UPGRADE_DONE;
+ HMX_UPGRADE_Call_Callback(upgrade_status_msg);
+
+ /* TASK kills itself. */
+ return 0;
+ }
+ case HMX_UPGRADE_FETCH:
+ {
+ printf("[%s] HMX_UPGRADE_FETCH \r\n",__FUNCTION__);
+ file_path = strdup(recieved_command.file_path);
+
+ printf("[%s] file path = %s \r\n",__FUNCTION__, file_path);
+
+ /* command file_path free */
+ free(recieved_command.file_path);
+
+ send_command.command = HMX_UPGRADE_START;
+ (void)HMX_MSG_Send(s_ulUpgradeMessgseId, &send_command, sizeof(HMX_UPGRADE_COMMAND_t),0);
+ break;
+ }
+
+ default:
+ printf("[%s] Receive Unknown Command \r\n",__FUNCTION__);
+ break;
+ }
+ }
+ }
+}
+
+/*@}*/
diff --git a/libupgrade/hmx_upgrade.h b/libupgrade/hmx_upgrade.h
new file mode 100644
index 0000000..5066c45
--- /dev/null
+++ b/libupgrade/hmx_upgrade.h
@@ -0,0 +1,139 @@
+/*******************************************************************/
+/************************* File Description ************************/
+/*******************************************************************/
+/* File Name: $Workfile: hmx_uprade.h $
+ * Version: $Revision: 1.0 $
+ * Original Author: Yang Hyun Uk $
+ * Current Author: $Author: huyang@humaxdigital.com $
+ * Date: $Date: 2011.09.30
+ * File Description: Upgrade APIs
+ * Module:
+ * Remarks:
+ */
+
+/**
+ * @defgroup UPGRADE Upgrade APIs
+ */
+
+/**
+ * @author Hyunuk Yang(huyang@humaxdigital.com)
+ * @date 30 Sept 2011
+ */
+
+/**
+ * @note
+ * Copyright (C) 2011 Humax Corporation. All Rights Reserved. <br>
+ * This software is the confidential and proprietary information
+ * of Humax Corporation. You may not use or distribute this software
+ * except in compliance with the terms and conditions of any applicable license
+ * agreement in writing between Humax Corporation and you.
+ */
+
+ /*@{*/
+
+/**
+ * @file hmx_upgrade.h
+ */
+
+/*******************************************************************/
+/**************************** Header Files**************************/
+/*******************************************************************/
+/* Start Including Header Files */
+#include <stdio.h>
+#include <string.h>
+#include <stdlib.h>
+#include <pthread.h>
+#include <errno.h>
+#include <assert.h>
+#include <sys/queue.h>
+#include <unistd.h>
+#include <fcntl.h>
+#include "hmx_upgrade_system.h"
+#include "hmx_upgrade_flash.h"
+/* End Including Headers*/
+
+/*******************************************************************/
+/************************ Extern variables *************************/
+/*******************************************************************/
+/* Start Extern variablee */
+
+/* End Extern variable */
+
+
+/*******************************************************************/
+/************************ Macro Definition *************************/
+/*******************************************************************/
+/* Start Macro definition */
+/* End Macro definition */
+
+
+
+/*******************************************************************/
+/****************************** typedef ****************************/
+/*******************************************************************/
+/* Start typedef */
+
+typedef enum
+{
+ HMX_UPGRADE_START, /**< */
+ HMX_UPGRADE_STOP, /**< */
+ HMX_UPGRADE_FETCH, /**< */
+}HMX_UPGRADE_COMMAND_e;
+
+typedef struct
+{
+ HMX_UPGRADE_COMMAND_e command;
+ unsigned char * file_path;
+}HMX_UPGRADE_COMMAND_t;
+
+/**
+ * HMX_UPGRADE Status cases.
+ */
+typedef enum
+{
+ HMX_UPGRADE_STARTED, /**< Upgrade Module is just started */
+ HMX_UPGRADE_GET_VERSION, /**< this comes with version information */
+ HMX_UPGRADE_READING, /**< reading file. Upgrade is in progress. */
+ HMX_UPGRADE_FLASHING, /**< Flashing. Upgrade is in progress. */
+ HMX_UPGRADE_DONE, /**< Upgrade is done without any error, After this message, Upgrade module will be destroy itself. */
+ HMX_UPGRADE_STOPED_BY_USER, /**< Upgrade is stopped by user. After this message, Upgrade module will be destroy itself. */
+ HMX_UPGRADE_FAILED, /**< Upgrade is failed, it shouldn't happen. After this message, Upgrade module will be destroy itself.*/
+ HMX_UPGRADE_VERSION_FAILED, /**< Upgrade is failed, version problem. */
+ HMX_UPGRADE_FILE_NOT_EXIST, /**< Upgrade is failed, there is no file exist */
+ HMX_UPGRADE_FILE_FORMAT_ERROR, /**< Upgrade is failed, file is not HDF Format */
+
+}HMX_UPGRADE_EVENT_e;
+
+
+/**
+ * HMX_UPGRADE_Status_Messages
+ */
+typedef struct
+{
+ HMX_UPGRADE_EVENT_e event; /**< event from Upgrade module */
+ unsigned int percentage; /**< percentage progress */
+ unsigned int current_version; /**< version current */
+ unsigned int version_to_upgrade; /**< version to upgrade */
+} HMX_UPGRADE_STATUS_Msg_t;
+
+/**
+ * Prototype of upgrade event callback function <br>
+ * Callback can be added by HMX_UPGRADE_Start <br><br>
+ * HMX_UPGRADE_READING, HMX_UPGRADE_FLASHING events always comes with value of percentage.
+ */
+typedef void (*HMX_UpgradeEventCallback) (HMX_UPGRADE_STATUS_Msg_t * UpgradeStatusMessages);
+
+/* End typedef */
+
+
+/*******************************************************************/
+/******************** global function prototype ********************/
+/*******************************************************************/
+/* Start global function prototypes */
+extern HMX_UpgradeEventCallback g_fUpgradeStatusCallback;
+/* End global function prototypes */
+
+int HMX_UPGRADE_Start( HMX_UpgradeEventCallback callback, unsigned char * file);
+int HMX_UPGRADE_Stop( void);
+
+/*@}*/
diff --git a/libupgrade/hmx_upgrade_flash.c b/libupgrade/hmx_upgrade_flash.c
new file mode 100644
index 0000000..46fa911
--- /dev/null
+++ b/libupgrade/hmx_upgrade_flash.c
@@ -0,0 +1,428 @@
+/*******************************************************************/
+/************************* File Description ************************/
+/*******************************************************************/
+/* File Name: $Workfile: hmx_uprade_flash.c $
+ * Version: $Revision: 1.0 $
+ * Original Author: Yang Hyun Uk $
+ * Current Author: $Author: huyang@humaxdigital.com $
+ * Date: $Date: 2011.09.30
+ * File Description: Humax Upgrade APIs
+ * Module:
+ * Remarks:
+ */
+
+/**
+ * @defgroup UPGRADE_FLASH Flashing APIs for Upgrade Module
+ * @ingroup UPGRADE
+ *
+ */
+
+/**
+ * @author Hyunuk Yang(huyang@humaxdigital.com)
+ * @date 30 Sept 2011
+ */
+
+/**
+ * @note
+ * Copyright (C) 2011 Humax Corporation. All Rights Reserved. <br>
+ * This software is the confidential and proprietary information
+ * of Humax Corporation. You may not use or distribute this software
+ * except in compliance with the terms and conditions of any applicable license
+ * agreement in writing between Humax Corporation and you.
+ */
+
+ /*@{*/
+
+/**
+ * @file hmx_upgrade_flash.c
+ */
+
+/*******************************************************************/
+/**************************** Header Files *************************/
+/*******************************************************************/
+/* Start Including Header Files */
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <fcntl.h>
+#include <unistd.h>
+#include <sys/ioctl.h>
+#include <sys/mount.h>
+#include <mtd/mtd-user.h>
+#include "hmx_upgrade_flash.h"
+/* End Including Headers */
+
+
+/*******************************************************************/
+/****************************** define *****************************/
+/*******************************************************************/
+/* End #define */
+/* this is for test */
+#define TARGET_BOOT_LOADER_MTD "/dev/mtdblock0"
+
+#define TARGET_NVRAM_MTD "/dev/mtdblock1"
+
+/* this is for test */
+#define TARGET_KERNEL_MTD "/dev/mtdblock10"
+
+/* this is for test ubi mapped */
+#define TARGET_ROOTFS_UBI_MTD "/dev/mtdblock11"
+
+
+
+
+/*******************************************************************/
+/****************************** typedef ****************************/
+/*******************************************************************/
+/* Start typedef */
+/* End typedef */
+
+
+/*******************************************************************/
+/************************ global variables *************************/
+/*******************************************************************/
+/* Start global variable */
+
+/* End global variable */
+
+
+/*******************************************************************/
+/************************ static variables *************************/
+/*******************************************************************/
+/* Start static variable */
+int fd_kernel = 0;
+int fd_rootfs = 0;
+int fd_boorloader = 0;
+int fd_nvram = 0;
+
+static unsigned long s_FlashTotalSize;
+static unsigned long s_FlashBlockSize;
+static unsigned char *s_BlockBuff;
+
+/* End static variable */
+int HMX_UPGRADE_Flash_Kernel(unsigned long offset, unsigned int size, unsigned char * data );
+int HMX_UPGRADE_Flash_Rootfs(unsigned long offset, unsigned int size, unsigned char * data );
+int HMX_UPGRADE_Flash_BootLoader(unsigned long offset, unsigned int size, unsigned char * data );
+
+
+
+unsigned char * HMX_UPGRADE_Get_Deactivated_Kernel_MTD(void)
+{
+ return TARGET_KERNEL_MTD;
+}
+
+unsigned char * HMX_UPGRADE_Get_Deactivated_Rootfs_MTD(void)
+{
+ return TARGET_ROOTFS_UBI_MTD;
+}
+
+/*******************************************************************/
+/************************ static funtions **************************/
+/*******************************************************************/
+
+int HMX_UPGRADE_NVRAM_Write(unsigned long offset, unsigned char * data, unsigned int size )
+{
+ int ret;
+ struct mtd_info_user info;
+ unsigned long block_size, write_size;
+ unsigned long mov_offset, remain_size;
+
+ printf("[%s] offset %08x, size %d, data = %02x\n",__FUNCTION__, offset, size, data[0] );
+
+ /* */
+ if ( fd_nvram == 0 )
+ {
+ fd_nvram = open(TARGET_NVRAM_MTD, (O_RDWR | O_SYNC) );
+ if( fd_nvram < 0 )
+ {
+ printf( "Failed to open!\n" );
+ return -1;
+ }
+ }
+
+ ret = ioctl(fd_nvram, MEMGETINFO,(void *)&info);
+ if(ret < 0)
+ {
+ printf("can't get info data! (%d)\n", ret);
+ return -1;
+ }
+
+ remain_size = size;
+ mov_offset = offset;
+
+ while(remain_size > 0)
+ {
+ /* offsetÀÌ block ³Ñ¾î¼¸é ¾ÈµÈ´Ù.. */
+ write_size = info.erasesize;
+ write_size -= ((mov_offset + info.erasesize)%info.erasesize);
+
+ /* ¸¶Áö¸·Àº ³ª¸ÓÁö ¸¸Å.. */
+ if( remain_size < write_size)
+ {
+ write_size = remain_size;
+ }
+
+ printf(" write : offset - 0x%x, size %d\n", mov_offset, write_size);
+
+ ret = lseek(fd_nvram, mov_offset, SEEK_SET);
+ if(ret < 0)
+ {
+ printf("can't seek position! (%d)\n", ret);
+ return -1;
+ }
+
+ ret = write(fd_nvram, data+(mov_offset-offset), write_size);
+ if(ret < 0)
+ {
+ printf("can't write data! (%d)\n", ret);
+ return -1;
+ }
+
+ mov_offset += write_size;
+ remain_size -= write_size;
+ }
+
+ return 0;
+}
+
+int HMX_UPGRADE_NVRAM_Read(unsigned long offset, unsigned char * data, unsigned int size )
+{
+ int ret;
+ struct mtd_info_user info;
+ unsigned long block_size, write_size;
+ unsigned long mov_offset, remain_size;
+
+ printf("[%s] offset %08x, size %d, data = %02x\n",__FUNCTION__, offset, size, data[0] );
+
+ /* */
+ if ( fd_nvram == 0 )
+ {
+ fd_nvram = open(TARGET_NVRAM_MTD, (O_RDWR | O_SYNC) );
+ if( fd_nvram < 0 )
+ {
+ printf( "Failed to open!\n" );
+ return -1;
+ }
+ }
+
+
+ ret = lseek(fd_nvram, offset, SEEK_SET);
+ if(ret < 0)
+ {
+ printf("can't seek position! (%d)\n", ret);
+ return -1;
+ }
+
+ ret = read(fd_nvram, data, size);
+ if(ret < 0)
+ {
+ printf("can't read data! (%d)\n", ret);
+ return ret;
+ }
+
+ return 0;
+}
+
+
+
+int HMX_UPGRADE_Flash_Kernel(unsigned long offset, unsigned int size, unsigned char * data )
+{
+ int ret;
+ unsigned char * com_buf;
+
+ printf("[%s] offset %08x, size %d, data = %02x\n",__FUNCTION__, offset, size, data[0] );
+ /* */
+ if ( fd_kernel == 0 )
+ {
+ fd_kernel = open(HMX_UPGRADE_Get_Deactivated_Kernel_MTD(), (O_RDWR | O_SYNC) );
+ if( fd_kernel < 0 )
+ {
+ printf( "Failed to open fd_kernel!\n" );
+ return -1;
+ }
+ }
+
+ ret = lseek(fd_kernel, offset, SEEK_SET);
+ if(ret < 0)
+ {
+ printf("failed seeking position! (%d)\n", ret);
+ return ret;
+ }
+
+ ret = write(fd_kernel, data, size);
+ if(ret < 0)
+ {
+ printf("can't write data! (%d)\n", ret);
+ return ret;
+ }
+
+ /* Read and Compare */
+ ret = lseek(fd_kernel, offset, SEEK_SET);
+ if(ret < 0)
+ {
+ printf("failed seeking position! (%d)\n", ret);
+ return ret;
+ }
+
+ com_buf = malloc(size);
+ if (com_buf == NULL )
+ {
+ printf("malloc faied!!! \n");
+ return -1;
+ }
+
+ ret = read(fd_kernel, com_buf, size);
+ if(ret < 0)
+ {
+ printf("can't read data! (%d)\n", ret);
+ return ret;
+ }
+
+ if ( memcmp(data, com_buf, size) != 0 )
+ {
+ printf("Written data is differnet!! \n");
+ return -1;
+ }
+
+ free(com_buf);
+
+ return 0;
+}
+
+int HMX_UPGRADE_Flash_BootLoader(unsigned long offset, unsigned int size, unsigned char * data )
+{
+ int ret;
+ struct mtd_info_user info;
+ unsigned long block_size, write_size;
+ unsigned long mov_offset, remain_size;
+
+ printf ( "SKIP BOOT LOADER... \n");
+ printf("[%s] offset %08x, size %d, data = %02x\n",__FUNCTION__, offset, size, data[0] );
+
+ return 0;
+
+ /* */
+ if ( fd_boorloader == 0 )
+ {
+ fd_boorloader = open(TARGET_BOOT_LOADER_MTD, (O_RDWR | O_SYNC) );
+ if( fd_boorloader < 0 )
+ {
+ printf( "Failed to open!\n" );
+ return -1;
+ }
+ }
+
+ ret = ioctl(fd_boorloader, MEMGETINFO,(void *)&info);
+ if(ret < 0)
+ {
+ printf("can't get info data! (%d)\n", ret);
+ return -1;
+ }
+
+ remain_size = size;
+ mov_offset = offset;
+
+ while(remain_size > 0)
+ {
+ /* offsetÀÌ block ³Ñ¾î¼¸é ¾ÈµÈ´Ù.. */
+ write_size = info.erasesize;
+ write_size -= ((mov_offset + info.erasesize)%info.erasesize);
+
+ /* ¸¶Áö¸·Àº ³ª¸ÓÁö ¸¸Å.. */
+ if( remain_size < write_size)
+ {
+ write_size = remain_size;
+ }
+
+ printf(" write : offset - 0x%x, size %d\n", mov_offset, write_size);
+
+ ret = lseek(fd_boorloader, mov_offset, SEEK_SET);
+ if(ret < 0)
+ {
+ printf("can't seek position! (%d)\n", ret);
+ return -1;
+ }
+
+ ret = write(fd_boorloader, data+(mov_offset-offset), write_size);
+ if(ret < 0)
+ {
+ printf("can't write data! (%d)\n", ret);
+ return -1;
+ }
+
+ mov_offset += write_size;
+ remain_size -= write_size;
+ }
+
+ return 0;
+}
+
+int HMX_UPGRADE_Flash_Rootfs(unsigned long offset, unsigned int size, unsigned char * data )
+{
+ int ret;
+ unsigned char * com_buf;
+ printf("[%s] offset %08x, size %d, data = %02x\n",__FUNCTION__, offset, size, data[0] );
+
+ /* */
+ if ( fd_rootfs == 0 )
+ {
+ fd_rootfs = open(HMX_UPGRADE_Get_Deactivated_Rootfs_MTD(), (O_RDWR | O_SYNC) );
+ if( fd_rootfs < 0 )
+ {
+ printf( "Failed to open fd_kernel!\n" );
+ return -1;
+ }
+ }
+
+ ret = lseek(fd_rootfs, offset, SEEK_SET);
+ if(ret < 0)
+ {
+ printf("failed seeking position! (%d)\n", ret);
+ return ret;
+ }
+
+ ret = write(fd_rootfs, data, size);
+ if(ret < 0)
+ {
+ printf("can't write data! (%d)\n", ret);
+ return ret;
+ }
+
+ /* Read and Compare */
+ ret = lseek(fd_rootfs, offset, SEEK_SET);
+ if(ret < 0)
+ {
+ printf("failed seeking position! (%d)\n", ret);
+ return ret;
+ }
+
+ com_buf = malloc(size);
+ if (com_buf == NULL )
+ {
+ printf("malloc faied!!! \n");
+ return -1;
+ }
+
+ ret = read(fd_rootfs, com_buf, size);
+ if(ret < 0)
+ {
+ printf("can't read data! (%d)\n", ret);
+ return ret;
+ }
+
+ if ( memcmp(data, com_buf, size) != 0 )
+ {
+ printf("Written data is differnet!! \n");
+ return -1;
+ }
+
+ free(com_buf);
+
+ return 0;
+
+
+}
+
+
+
+/*@}*/
diff --git a/libupgrade/hmx_upgrade_flash.h b/libupgrade/hmx_upgrade_flash.h
new file mode 100644
index 0000000..674f05b
--- /dev/null
+++ b/libupgrade/hmx_upgrade_flash.h
@@ -0,0 +1,74 @@
+/*******************************************************************/
+/************************* File Description ************************/
+/*******************************************************************/
+/* File Name: $Workfile: hmx_uprade_flash.h $
+ * Version: $Revision: 1.0 $
+ * Original Author: Yang Hyun Uk $
+ * Current Author: $Author: huyang@humaxdigital.com $
+ * Date: $Date: 2011.09.30
+ * File Description: Humax Upgrade APIs
+ * Module:
+ * Remarks:
+ */
+
+/**
+ * @author Hyunuk Yang(huyang@humaxdigital.com)
+ * @date 30 Sept 2011
+ */
+
+/**
+ * @note
+ * Copyright (C) 2011 Humax Corporation. All Rights Reserved. <br>
+ * This software is the confidential and proprietary information
+ * of Humax Corporation. You may not use or distribute this software
+ * except in compliance with the terms and conditions of any applicable license
+ * agreement in writing between Humax Corporation and you.
+ */
+
+ /*@{*/
+
+/**
+ * @file hmx_upgrade_flash.h
+ */
+
+/*******************************************************************/
+/**************************** Header Files**************************/
+/*******************************************************************/
+/* Start Including Header Files */
+
+/* End Including Headers*/
+
+/*******************************************************************/
+/************************ Extern variables *************************/
+/*******************************************************************/
+/* Start Extern variablee */
+
+/* End Extern variable */
+
+
+/*******************************************************************/
+/************************ Macro Definition *************************/
+/*******************************************************************/
+/* Start Macro definition */
+
+/* End Macro definition */
+
+
+
+/*******************************************************************/
+/****************************** typedef ****************************/
+/*******************************************************************/
+/* Start typedef */
+
+
+/* End typedef */
+
+
+/*******************************************************************/
+/******************** global function prototype ********************/
+/*******************************************************************/
+/* Start global function prototypes */
+
+/* End global function prototypes */
+
+/*@}*/
diff --git a/libupgrade/hmx_upgrade_nvram.c b/libupgrade/hmx_upgrade_nvram.c
new file mode 100644
index 0000000..63bcbf5
--- /dev/null
+++ b/libupgrade/hmx_upgrade_nvram.c
@@ -0,0 +1,1090 @@
+/*******************************************************************/
+/************************* File Description ************************/
+/*******************************************************************/
+/* File Name: $Workfile: hmx_uprade_nvram.c $
+ * Version: $Revision: 1.0 $
+ * Original Author: Yang Hyun Uk $
+ * Current Author: $Author: huyang@humaxdigital.com $
+ * Date: $Date: 2011.11.07
+ * File Description: Humax Upgrade APIs
+ * Module:
+ * Remarks:
+ */
+
+/**
+ * @defgroup NVRAM APIs for Upgrade Module
+ * @ingroup UPGRADE
+ */
+
+/**
+ * @author Hyunuk Yang(huyang@humaxdigital.com)
+ * @date 07 Nov 2011
+ */
+
+/**
+ * @note
+ * Copyright (C) 2011 Humax Corporation. All Rights Reserved. <br>
+ * This software is the confidential and proprietary information
+ * of Humax Corporation. You may not use or distribute this software
+ * except in compliance with the terms and conditions of any applicable license
+ * agreement in writing between Humax Corporation and you.
+ */
+
+ /*@{*/
+
+/**
+ * @file hmx_upgrade_nvram.c
+ */
+
+/*******************************************************************/
+/**************************** Header Files *************************/
+/*******************************************************************/
+/* Start Including Header Files */
+#include <stdio.h>
+#include <string.h>
+#include <stdlib.h>
+
+#include "lib_queue.h"
+#include "hmx_upgrade_nvram.h"
+/* End Including Headers */
+
+
+/*******************************************************************/
+/****************************** define *****************************/
+/*******************************************************************/
+
+#define NVRAM_TYPE_LEN 1
+#define NVRAM_RECORD_LENG_LEN 4
+#define NVRAM_NAME_LENG_LEN 1
+#define NVRAM_DATA_LENG_LEN 4
+
+#define MAX_NAME_LEN (256)
+#define MAX_DATA_LEN (256*1024)
+#define MAX_FIELD_LEN (MAX_DATA_LEN+MAX_NAME_LEN*2)
+
+#define NVRAM_TLV_TYPE_END 0x00
+#define NVRAM_TLV_TYPE_ENV 0x01
+
+#define get8bit(q) (unsigned char)((q)[0])
+#define get32bit(q) (unsigned int)(((*(unsigned char *)(q)) << 24) | (*((unsigned char *)(q)+1) << 16) | (*((unsigned char *)(q)+2) << 8) | (*((unsigned char *)(q)+3)) )
+
+#define DEBUG_ERR printf
+#define DEBUG_INFO printf
+#define UNUSED(x) (void)(x)
+
+#define MAX_NVRAM_FILENAME_LENGTH 32
+
+#define SEM_Get(x) (void)(x)
+#define SEM_Release(x) (void)(x)
+
+#define NVRAM_RO_OFFSET 0x0
+#define NVRAM_RO_SIZE 0x00080000
+#define NVRAM_RW_OFFSET ( NVRAM_RO_OFFSET + NVRAM_RO_SIZE )
+#define NVRAM_RW_SIZE 0x00020000
+#define NVRAM_RWB_OFFSET ( NVRAM_RW_OFFSET + NVRAM_RW_SIZE)
+#define NVRAM_RWB_SIZE 0x00020000
+#define RAW_FS_OFFSET ( NVRAM_RWB_OFFSET + NVRAM_RWB_SIZE)
+#define RAW_FS_SIZE 0x00020000
+
+/* End #define */
+
+/*******************************************************************/
+/****************************** typedef ****************************/
+/*******************************************************************/
+/* Start typedef */
+
+typedef struct NVRAM_EVNVAR_t{
+ queue_t qb;
+ unsigned int recLen;
+ unsigned char *name;
+ unsigned char nameLen;
+ unsigned char *value;
+ unsigned int valueLen;
+} NVRAM_EVNVAR_T;
+
+
+
+typedef struct HMX_NVRAM_MAP_t
+{
+ NVRAM_FIELD_T type;
+ unsigned char szFileName[MAX_NVRAM_FILENAME_LENGTH];
+ HMX_NVRAM_PARTITION_E storePartition;
+ unsigned int defaultSize;
+} HMX_NVRAM_FIELD_INFO_T;
+
+HMX_NVRAM_FIELD_INFO_T s_nvramFieldInfo[] =
+{
+ {NVRAM_FIELD_SYSTEM_ID , "SYSTEM_ID" , HMX_NVRAM_PARTITION_RO, 0},
+ {NVRAM_FIELD_SFLASH , "SFLASH" , HMX_NVRAM_PARTITION_RO, 0},
+ {NVRAM_FIELD_SERIAL_NO , "SERIAL_NO" , HMX_NVRAM_PARTITION_RO, 0},
+ {NVRAM_FIELD_DTCP_KEY , "DTCP_KEY" , HMX_NVRAM_PARTITION_RO, 0},
+ {NVRAM_FIELD_CI_PLUS_KEY , "CI_PLUS_KEY" , HMX_NVRAM_PARTITION_RO, 0},
+ {NVRAM_FIELD_MAC_ADDR , "MAC_ADDR" , HMX_NVRAM_PARTITION_RO, 0},
+ {NVRAM_FIELD_HDCP_KEY , "HDCP_KEY" , HMX_NVRAM_PARTITION_RO, 0},
+ {NVRAM_FIELD_PARING_DATA , "PARING_DATA" , HMX_NVRAM_PARTITION_RO, 0},
+ {NVRAM_FIELD_CM_SERIAL_NO , "CM_SERIAL_NO" , HMX_NVRAM_PARTITION_RO, 0},
+ {NVRAM_FIELD_CM_MAC_ADDR , "CM_MAC_ADDR" , HMX_NVRAM_PARTITION_RO, 0},
+ {NVRAM_FIELD_CM_MAC_ADDR_ANOTHER , "CM_MAC_ADDR_ANOTHER" , HMX_NVRAM_PARTITION_RO, 0},
+ {NVRAM_FIELD_IRDETO_BBCB , "IRDETO_BBCB" , HMX_NVRAM_PARTITION_RO, 0},
+ {NVRAM_FIELD_IRDETO_CPCB , "IRDETO_CPCB" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_IRDETO_CPCB_ENCRYPTED, "IRDETO_CPCB_ENCRYPTED" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_PRIVATE , "PRAVATE" , HMX_NVRAM_PARTITION_RO, 0},
+ {NVRAM_FIELD_CSC_KEY , "CSC_KEY" , HMX_NVRAM_PARTITION_RO, 0},
+ {NVRAM_FIELD_LOADER_VER , "LOADER_VER" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_APP_VER , "APP_VER" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_LANGUAGE , "LANGUAGE" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_TV_STANDARD , "TV_STANDARD" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_SCART_RGB , "SCART_RGB" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_HD_RESOULTION , "HD_RESOULTION" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_FIELD_RATE , "FIELD_RATE" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_OTA_FLAG1 , "OTA_FLAG1" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_OTA_FLAG2 , "OTA_FLAG2" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_OTA_FLAG3 , "OTA_FLAG3" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_OTA_TYPE1 , "OTA_TYPE1" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_OTA_TYPE2 , "OTA_TYPE2" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_OTA_TYPE3 , "OTA_TYPE3" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_CH_TYPE1 , "CH_TYPE1" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_CH_TYPE2 , "CH_TYPE2" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_CH_TYPE3 , "CH_TYPE3" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_TUNER_ID1 , "TUNER_ID1" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_TUNER_ID2 , "TUNER_ID2" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_TUNER_ID3 , "TUNER_ID3" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_ANTENA_POWER1 , "ANTENA_POWER1" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_ANTENA_POWER2 , "ANTENA_POWER2" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_ANTENA_POWER3 , "ANTENA_POWER3" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_ES_PID1 , "ES_PID1" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_ES_PID2 , "ES_PID2" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_ES_PID3 , "ES_PID3" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_TRANSACTION_ID1 , "TRANSACTION_ID1" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_TRANSACTION_ID2 , "TRANSACTION_ID2" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_TRANSACTION_ID3 , "TRANSACTION_ID3" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_APP_VERSION , "APP_VERSION" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_OTALDR_VERSION , "OTALDR_VERSION" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_CUR_OTAIMAGE_VERSION , "CUR_OTAIMAGE_VERSION" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_OAD_VERSION , "OAD_VERSION" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_NET_IP_CONFIG , "NET_IP_CONFIG" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_NET_IP_SETTING , "NET_IP_SETTING" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_RCU_CUSTOM_CODE , "RCU_CUSTOM_CODE" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_RCU_CUSTOM_CODE2 , "RCU_CUSTOM_CODE2" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_PANEL_DISPLAY , "PANEL_DISPLAY" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_PANEL_DIMMING , "PANEL_DIMMING" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_ASPECT_RATIO , "ASPECT_RATIO" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_COUNTRY_CODE , "COUNTRY_CODE" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_USAGE_ID , "USAGE_ID" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_CH_INFO_S , "CH_INFO_S" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_CH_INFO_T , "CH_INFO_T" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_CH_INFO_C , "CH_INFO_C" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_OTA_FTP_INFO , "FTP_OTA_INFO" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_NET_PORTAL_IP , "NET_PORTAL_IP" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_NET_DOWN_PATH , "NET_DOWN_PATH" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_LOADER_VERSION , "LOADER_VERSION" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_OSD_DISPLAY , "OSD_DISPLAY" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_ACTIVATED_KERNEL_NUM, "ACTIVATED_KERNEL_NUM" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_ACTIVATED_ROOTFS_NUM , "ACTIVATED_ROOTFS_NUM" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_MTD_TYPE_FOR_KERNEL , "MTD_TYPE_FOR_KERNEL" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_TYPE_OF_FILESYSTEM , "TYPE_OF_FILESYSTEM" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_NAME_OF_BOARD , "NAME_OF_BOARD" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_L_TYPE_OF_FILESYSTEM , "L_TYPE_OF_FILESYSTEM" , HMX_NVRAM_PARTITION_RW, 0},
+ {NVRAM_FIELD_L_NAME_OF_BOARD , "L_NAME_OF_BOARD" , HMX_NVRAM_PARTITION_RW, 0},
+
+ {NVRAM_FIELD_BIN8K , "BIN8K" , HMX_NVRAM_PARTITION_RW, 0x2000},
+ {NVRAM_FIELD_RAWFS , "RAWFS" , HMX_NVRAM_PARTITION_W_RAWFS, RAW_FS_SIZE},
+ {NVRAM_FIELD_DUMMY , "DUMMY" , HMX_NVRAM_PARTITION_RW, 0}
+};
+
+/* End typedef */
+
+/*******************************************************************/
+/************************ global variables *************************/
+/*******************************************************************/
+/* Start global variable */
+static queue_t s_nvram_envvars[HMX_NVRAM_PARTITION_MAX] = {
+ {&s_nvram_envvars[0],&s_nvram_envvars[0]},
+ {&s_nvram_envvars[1],&s_nvram_envvars[1]},
+ {&s_nvram_envvars[2],&s_nvram_envvars[2]},
+ };
+
+static unsigned int s_nvram_offset[HMX_NVRAM_PARTITION_MAX] = {
+ NVRAM_RO_OFFSET,
+ NVRAM_RW_OFFSET,
+ RAW_FS_OFFSET
+ };
+
+static unsigned int s_nvram_backup_offset[HMX_NVRAM_PARTITION_MAX] = {
+ 0,
+ NVRAM_RWB_OFFSET,
+ 0
+ };
+
+static unsigned int s_nvram_size[HMX_NVRAM_PARTITION_MAX] = {
+ NVRAM_RO_SIZE,
+ NVRAM_RW_SIZE,
+ RAW_FS_SIZE
+ };
+
+/* End global variable */
+
+
+/*******************************************************************/
+/************************ static variables *************************/
+/*******************************************************************/
+/* Start static variable */
+static unsigned long s_nvramSema;
+
+
+/* End static variable */
+
+
+/*******************************************************************/
+/************************ static funtions **************************/
+/*******************************************************************/
+/* *********************************************************************0
+ * HMX_NVRAM_Read(buffer,offset,length)0
+ * 0
+ * Read data from the NVRAM device0
+ *
+ * Input parameters:
+ * buffer - destination buffer
+ * offset - offset of data to read
+ * length - number of bytes to read
+ *
+ * Return value:
+ * number of bytes read, or <0 if error occured
+ ********************************************************************* */
+static int drv_NVRAM_Read(unsigned char *buffer,unsigned int offset,unsigned int length)
+{
+ DRV_Error drv_error;
+
+ drv_error = HMX_UPGRADE_NVRAM_Read(offset, buffer, length);
+ if (drv_error != 0)
+ {
+ return -1;
+ }
+
+ return length;
+}
+
+/* *********************************************************************
+ * HMX_NVRAM_Write(buffer,offset,length)
+ *
+ * Write data to the NVRAM device
+ *
+ * Input parameters:
+ * buffer - source buffer
+ * offset - offset of data to write
+ * length - number of bytes to write
+ *
+ * Return value:
+ * number of bytes written, or -1 if error occured
+ ********************************************************************* */
+static int drv_NVRAM_Write(unsigned char *buffer,unsigned int offset,unsigned int length)
+{
+ DRV_Error drv_error;
+
+ drv_error = HMX_UPGRADE_NVRAM_Write(offset, buffer, length);
+ if (drv_error != 0)
+ {
+ return -1;
+ }
+
+ return length;
+}
+
+/* *********************************************************************
+ * HMX_NVRAM_FindEnv(name)
+ *
+ * Locate an environment variable in the in-memory list
+ *
+ * Input parameters:
+ * name - name of env var to find
+ *
+ * Return value:
+ * NVRAM_EVNVAR_T pointer, or NULL if not found
+ ********************************************************************* */
+
+static NVRAM_EVNVAR_T *drv_NVRAM_FindEnv(HMX_NVRAM_PARTITION_E partition, const unsigned char *name)
+{
+ queue_t *qb;
+ NVRAM_EVNVAR_T *env;
+
+ for (qb = s_nvram_envvars[partition].q_next; qb != &s_nvram_envvars[partition]; qb = qb->q_next)
+ {
+ env = (NVRAM_EVNVAR_T *) qb;
+ if (strcmp((char*)env->name, (char*)name) == 0)
+ break;
+ }
+
+ if (qb == &s_nvram_envvars[partition])
+ return NULL;
+
+ return (NVRAM_EVNVAR_T *) qb;
+
+}
+
+/* *********************************************************************
+ * HMX_NVRAM_ScanDir(idx,name,namelen,val,vallen)
+ *
+ * Enumerate environment variables. This routine locates
+ * the nth environment variable and copies its name and value
+ * to user buffers.
+ *
+ * The namelen and vallen variables must be preinitialized to
+ * the maximum size of the output buffer.
+ *
+ * Input parameters:
+ * idx - variable index to find (starting with zero)
+ * name,namelen - name buffer and length
+ * val,vallen - value buffer and length
+ *
+ * Return value:
+ * 0 if ok
+ * else error code
+ ********************************************************************* */
+
+static DRV_Error drv_NVRAM_ScanDir(HMX_NVRAM_PARTITION_E partition, unsigned int idx, unsigned char *name, unsigned int *namelen, unsigned char *val, unsigned int *vallen)
+{
+ queue_t *qb;
+ NVRAM_EVNVAR_T *env;
+
+ for (qb = s_nvram_envvars[partition].q_next; qb != &s_nvram_envvars[partition]; qb = qb->q_next) {
+ if (idx == 0)
+ break;
+ idx--;
+ }
+
+ if (qb == &s_nvram_envvars[partition])
+ {
+ return DRV_ERR;
+ }
+ env = (NVRAM_EVNVAR_T *) qb;
+
+ if (name != NULL)
+ {
+ strncpy((char*)name, (char*)env->name, env->nameLen);
+ name[env->nameLen] = 0;
+ }
+ *namelen = env->nameLen;
+ if (val != NULL)
+ {
+ memcpy(val, env->value, env->valueLen);
+ }
+ *vallen = env->valueLen;
+
+ return DRV_OK;
+}
+
+/* *********************************************************************
+ * HMX_NVRAM_Delete(name)
+ *
+ * Delete an environment variable
+ *
+ * Input parameters:
+ * name - environment variable to delete
+ *
+ * Return value:
+ * 0 if ok
+ * else error code
+ ********************************************************************* */
+
+static DRV_Error drv_NVRAM_Delete(HMX_NVRAM_PARTITION_E partition, const unsigned char *name)
+{
+ NVRAM_EVNVAR_T *env;
+
+ env = drv_NVRAM_FindEnv(partition, name);
+ if (env == NULL)
+ {
+ return DRV_ERR;
+ }
+
+ q_dequeue((queue_t *) env);
+ free(env);
+ return DRV_OK;
+}
+
+/* *********************************************************************
+ * HMX_NVRAM_GetEnv(name)
+ *
+ * Retrieve the value of an environment variable
+ *
+ * Input parameters:
+ * name - name of environment variable to find
+ *
+ * Return value:
+ * value, or NULL if variable is not found
+ ********************************************************************* */
+
+static DRV_Error drv_NVRAM_GetEnv(HMX_NVRAM_PARTITION_E partition, const unsigned char *name, const unsigned int offset, unsigned char *value, unsigned int readLen)
+{
+ NVRAM_EVNVAR_T *env;
+ unsigned int len;
+
+ memset(value, 0, readLen);
+ env = drv_NVRAM_FindEnv(partition, name);
+ if (env != NULL)
+ {
+ if (readLen > env->valueLen - offset)
+ len = env->valueLen - offset;
+ else
+ len = readLen;
+
+ memcpy(value, env->value+offset, len);
+ }
+
+ return DRV_OK;
+}
+
+/* *********************************************************************
+ * HMX_NVRAM_GetLength(name)
+ *
+ * Retrieve the value of an environment variable
+ *
+ * Input parameters:
+ * name - name of environment variable to find
+ *
+ * Return value:
+ * value, or NULL if variable is not found
+ ********************************************************************* */
+
+static DRV_Error drv_NVRAM_GetLength(HMX_NVRAM_PARTITION_E partition, const unsigned char *name, unsigned int *pLen)
+{
+ NVRAM_EVNVAR_T *env;
+
+ env = drv_NVRAM_FindEnv(partition, name);
+ if (env != NULL)
+ {
+ *pLen = env->valueLen;
+ return DRV_OK;
+ }
+
+ return DRV_ERR_INVALID_PARAMETER;
+}
+
+/* *********************************************************************
+ * HMX_NVRAM_SetEnv(name,value,flags)
+ *
+ * Set the value of an environment variable
+ *
+ * Input parameters:
+ * name - name of variable
+ * value - value of variable
+ * flags - flags for variable (ENV_FLG_xxx)
+ *
+ * Return value:
+ * 0 if ok
+ * else error code
+ ********************************************************************* */
+
+static DRV_Error drv_NVRAM_SetEnv(HMX_NVRAM_PARTITION_E partition, const unsigned char *name, unsigned char *value, unsigned int valueLen)
+{
+ NVRAM_EVNVAR_T *env;
+ unsigned int namelen;
+
+ env = drv_NVRAM_FindEnv(partition, name);
+ if (env)
+ {
+ q_dequeue((queue_t *) env);
+ free(env);
+ }
+
+ namelen = strlen((char*)name);
+ env = malloc(sizeof(NVRAM_EVNVAR_T) + namelen + 1 + valueLen);
+ if (!env)
+ {
+ return DRV_ERR_OUTOFMEMORY;
+ }
+ env->name = (unsigned char *) (env+1);
+ env->value = env->name + namelen + 1;
+ env->nameLen = namelen;
+ env->valueLen = valueLen;
+ env->recLen = (NVRAM_NAME_LENG_LEN + namelen + NVRAM_DATA_LENG_LEN + valueLen);
+
+ strncpy((char*)env->name, (char*)name, namelen);
+ env->name[namelen] = 0;
+ memcpy(env->value, value, valueLen);
+
+ q_enqueue(&s_nvram_envvars[partition],(queue_t *) env);
+
+ return DRV_OK;
+}
+
+
+/* *********************************************************************
+ * HMX_NVRAM_Load()
+ *
+ * Load the environment from the NVRAM device.
+ *
+ * Input parameters:
+ * nothing
+ *
+ * Return value:
+ * 0 if ok
+ * else error code
+ ********************************************************************* */
+
+
+static DRV_Error drv_NVRAM_LoadByAddress(HMX_NVRAM_PARTITION_E partition, unsigned int address, unsigned int size)
+{
+ unsigned int nvram_size;
+ unsigned char *buffer;
+ unsigned char *ptr;
+ unsigned int recLen;
+ unsigned int recType;
+ unsigned int offset;
+ unsigned int retval;
+ unsigned char fileName[MAX_NAME_LEN];
+ unsigned char nameLen;
+ unsigned int dataLen;
+
+ nvram_size = size;
+ buffer = malloc(MAX_FIELD_LEN);
+ if (buffer == NULL)
+ {
+ return DRV_ERR_OUTOFMEMORY;
+ }
+
+ ptr = buffer;
+ offset = 0;
+
+ retval = DRV_OK;
+ /* Read the record type and length */
+ if (drv_NVRAM_Read(ptr,offset+address,NVRAM_TYPE_LEN) != NVRAM_TYPE_LEN)
+ {
+ retval = DRV_ERR_EXTERNAL_ERROR;
+ goto error;
+ }
+
+ while ((*ptr != NVRAM_TLV_TYPE_END) && (nvram_size > NVRAM_TYPE_LEN))
+ {
+ /* Adjust pointer for TLV type */
+ recType = get8bit(ptr);
+ nvram_size -= NVRAM_TYPE_LEN;
+ offset += NVRAM_TYPE_LEN;
+
+ if (recType != NVRAM_TLV_TYPE_ENV)
+ {
+ retval = DRV_ERR_EVENT_INITIALIZATION;
+ goto error;
+ }
+
+ /* Read the record type and length - 16 bits, MSB first */
+ if (drv_NVRAM_Read(ptr, offset+address, NVRAM_RECORD_LENG_LEN) != NVRAM_RECORD_LENG_LEN)
+ {
+ retval = DRV_ERR_EXTERNAL_ERROR;
+ goto error;
+ }
+ recLen = get32bit(ptr);
+ nvram_size -= NVRAM_RECORD_LENG_LEN;
+ offset += NVRAM_RECORD_LENG_LEN;
+
+ if (recLen > MAX_FIELD_LEN)
+ {
+ retval = DRV_ERR_EVENT_INITIALIZATION;
+ goto error;
+ }
+ if (recLen > nvram_size)
+ {
+ retval = DRV_ERR_EVENT_INITIALIZATION;
+ goto error; /* should not happen, bad NVRAM */
+ }
+
+ /* Read the TLV data */
+ if (drv_NVRAM_Read(ptr,offset+address,recLen) != (int)recLen)
+ {
+ retval = DRV_ERR_EXTERNAL_ERROR;
+ goto error;
+ }
+
+ nameLen = get8bit(ptr);
+ ptr += NVRAM_NAME_LENG_LEN;
+ if (nameLen)
+ {
+ memcpy(fileName, ptr, nameLen);
+ }
+ fileName[nameLen] = 0;
+ ptr += nameLen;
+
+ dataLen = get32bit(ptr);
+ ptr += NVRAM_DATA_LENG_LEN;
+ if (dataLen > MAX_DATA_LEN)
+ {
+ retval = DRV_ERR_EVENT_INITIALIZATION;
+ goto error;
+ }
+
+ if (recLen != (NVRAM_NAME_LENG_LEN + nameLen + NVRAM_DATA_LENG_LEN + dataLen))
+ {
+ retval = DRV_ERR_EVENT_INITIALIZATION;
+ goto error;
+ }
+
+ drv_NVRAM_SetEnv(partition, fileName, ptr, dataLen);
+
+ nvram_size -= (unsigned int)recLen;
+ offset += recLen;
+
+ /* Read the next record type */
+ ptr = buffer;
+ if (drv_NVRAM_Read(ptr,offset+address, NVRAM_TYPE_LEN) != NVRAM_TYPE_LEN)
+ {
+ retval = DRV_ERR_EXTERNAL_ERROR;
+ goto error;
+ }
+ }
+
+error:
+ free(buffer);
+
+ return retval;
+
+}
+
+static DRV_Error drv_NVRAM_Load(HMX_NVRAM_PARTITION_E partition)
+{
+ DRV_Error drv_error;
+
+ drv_error = drv_NVRAM_LoadByAddress(partition, s_nvram_offset[partition], s_nvram_size[partition]);
+ if (drv_error != DRV_OK)
+ {
+ printf("[HMX_NVRAM_Load] error(%d) loading partition (%d)\n", drv_error, partition);
+ if (s_nvram_backup_offset[partition] != 0)
+ {
+ drv_error = drv_NVRAM_LoadByAddress(partition, s_nvram_backup_offset[partition], s_nvram_size[partition]);
+ if (drv_error != DRV_OK)
+ {
+ printf("[HMX_NVRAM_Load] error(%d) loading backup partition (%d)\n", drv_error, partition);
+ }
+ else
+ {
+ printf("[HMX_NVRAM_Load] load OK loading backup partition (%d)\n", partition);
+ }
+ }
+ }
+ return drv_error;
+}
+
+/* *********************************************************************
+ * HMX_NVRAM_Save()
+ *
+ * Write the environment to the NVRAM device.
+ *
+ * Input parameters:
+ * nothing
+ *
+ * Return value:
+ * 0 if ok, else error code
+ ********************************************************************* */
+
+static DRV_Error drv_NVRAM_Save(HMX_NVRAM_PARTITION_E partition)
+{
+ unsigned int nvram_size;
+ unsigned char *buffer;
+ unsigned char *buffer_end;
+ unsigned char *ptr;
+ queue_t *qb;
+ NVRAM_EVNVAR_T *env;
+ unsigned char namelen;
+ unsigned int valuelen;
+ unsigned int recLen;
+
+ nvram_size = s_nvram_size[partition];
+ buffer = malloc(nvram_size);
+ if (buffer == NULL)
+ {
+ return DRV_ERR_OUTOFMEMORY;
+ }
+ buffer_end = buffer + nvram_size - 1;
+
+ ptr = buffer;
+
+ for (qb = s_nvram_envvars[partition].q_next; qb != &s_nvram_envvars[partition]; qb = qb->q_next)
+ {
+ env = (NVRAM_EVNVAR_T *) qb;
+
+ namelen = env->nameLen;
+ valuelen = env->valueLen;
+ recLen = env->recLen;
+
+ if ((ptr + NVRAM_TYPE_LEN + NVRAM_RECORD_LENG_LEN + recLen) > buffer_end)
+ {
+ break;
+ }
+
+ *ptr++ = NVRAM_TLV_TYPE_ENV; /* TLV record type */
+
+ *ptr++ = (recLen>>24) & 0xFF; /* TLV record length */
+ *ptr++ = (recLen>>16) & 0xFF; /* TLV record length */
+ *ptr++ = (recLen>>8) & 0xFF; /* TLV record length */
+ *ptr++ = (recLen>>0) & 0xFF; /* TLV record length */
+
+ *ptr++ = (namelen>>0) & 0xFF; /* NAME record length */
+
+ memcpy(ptr, env->name, namelen); /* NAME record data */
+ ptr += namelen;
+
+ *ptr++ = (valuelen>>24) & 0xFF; /* VALUE record length */
+ *ptr++ = (valuelen>>16) & 0xFF; /* VALUE record length */
+ *ptr++ = (valuelen>>8) & 0xFF; /* VALUE record length */
+ *ptr++ = (valuelen>>0) & 0xFF; /* VALUE record length */
+
+ memcpy(ptr,env->value, valuelen);
+ ptr += valuelen;
+
+ }
+
+ *ptr++ = NVRAM_TLV_TYPE_END;
+
+ nvram_size = drv_NVRAM_Write(buffer,0+s_nvram_offset[partition],ptr-buffer);
+ if (s_nvram_backup_offset[partition] != 0)
+ {
+ drv_NVRAM_Write(buffer,0+s_nvram_backup_offset[partition],ptr-buffer);
+ }
+
+ free(buffer);
+
+ return (nvram_size == (unsigned int)(ptr-buffer)) ? DRV_OK : DRV_ERR_EXTERNAL_ERROR;
+}
+
+static unsigned int NVRAM_SWAP32(unsigned int A)
+{
+ return ((A << 24) | ((A << 8) & 0xFF0000) | ((A >> 8) & 0xFF00) |(A >> 24));
+}
+
+static unsigned long s_nvramSema;
+
+static DRV_Error drv_NVRAM_GetFieldInfo(const NVRAM_FIELD_T type, HMX_NVRAM_PARTITION_E *pPartition, unsigned char *pszFileName, unsigned int *defaultSize)
+{
+ int i;
+
+ SEM_Get(s_nvramSema);
+ for (i=0;;i++)
+ {
+ if (NVRAM_FIELD_DUMMY == s_nvramFieldInfo[i].type)
+ break;
+ if (type != s_nvramFieldInfo[i].type)
+ continue;
+ strncpy((char*)pszFileName, (char*)(s_nvramFieldInfo[i].szFileName), MAX_NVRAM_FILENAME_LENGTH);
+ *pPartition = s_nvramFieldInfo[i].storePartition;
+ *defaultSize = s_nvramFieldInfo[i].defaultSize;
+ SEM_Release(s_nvramSema);
+ return DRV_OK;
+ }
+ SEM_Release(s_nvramSema);
+ return 1;
+}
+
+
+DRV_Error HMX_NVRAM_Init(void)
+{
+ drv_NVRAM_Load(HMX_NVRAM_PARTITION_RO);
+ drv_NVRAM_Load(HMX_NVRAM_PARTITION_RW);
+ return DRV_OK;
+}
+
+DRV_Error HMX_NVRAM_Write(HMX_NVRAM_PARTITION_E partition, unsigned char *pName, unsigned int offset, unsigned char *pValue, unsigned int ulSize)
+{
+ DRV_Error drv_error;
+
+ UNUSED(offset);
+
+ SEM_Get(s_nvramSema);
+ drv_error = drv_NVRAM_SetEnv(partition, pName, pValue, ulSize);
+ drv_error = drv_NVRAM_Save(partition);
+ SEM_Release(s_nvramSema);
+ return drv_error;
+}
+
+DRV_Error HMX_NVRAM_Read(HMX_NVRAM_PARTITION_E partition, unsigned char *pName, unsigned int offset, unsigned char *pValue, unsigned int ulSize)
+{
+ DRV_Error drv_error;
+
+ SEM_Get(s_nvramSema);
+ memset(pValue, 0, ulSize);
+ drv_error = drv_NVRAM_GetEnv(partition, pName, offset, pValue, ulSize);
+ SEM_Release(s_nvramSema);
+ return drv_error;
+}
+
+DRV_Error HMX_NVRAM_GetField(NVRAM_FIELD_T field, unsigned int offset, void *data, int nDataSize)
+{
+ DRV_Error errCode = DRV_ERR;
+ unsigned char szFileName[MAX_NVRAM_FILENAME_LENGTH];
+ HMX_NVRAM_PARTITION_E partition;
+ int nvramHandle;
+ unsigned int defaultSize;
+
+ if( data == NULL || field == NVRAM_FIELD_DUMMY )
+ {
+ return 2;
+ }
+
+ errCode = drv_NVRAM_GetFieldInfo(field, &partition, szFileName, &defaultSize);
+ if (errCode != DRV_OK)
+ {
+ DEBUG_ERR("[HMX_NVRAM_GetField] field(%d) error(%08X) : HMX_NVRAM_GetFieldInfo\n", field, errCode);
+ return errCode;
+ }
+
+ switch (partition)
+ {
+ case HMX_NVRAM_PARTITION_W_RAWFS :
+ break;
+ case HMX_NVRAM_PARTITION_RO :
+ case HMX_NVRAM_PARTITION_RW :
+ if (defaultSize == 0)
+ {
+ errCode = HMX_NVRAM_Read(partition, szFileName, offset, data, nDataSize);
+ if (errCode != DRV_OK)
+ {
+ DEBUG_ERR("[HMX_NVRAM_GetField] field(%d)-%s error(%08X) : HMX_NVRAM_Read\n", field, szFileName, errCode);
+ return errCode;
+ }
+ if (field == NVRAM_FIELD_SYSTEM_ID && errCode == 0)
+ {
+ *((unsigned int*)data) = NVRAM_SWAP32((unsigned int)*(unsigned int*)data);
+ }
+ }
+ else
+ {
+ unsigned char *pBuf;
+
+ pBuf = malloc(defaultSize);
+ if (pBuf == NULL)
+ {
+ DEBUG_ERR("[HMX_NVRAM_GetField] malloc\n");
+ return 3;
+ }
+ errCode = HMX_NVRAM_Read(partition, szFileName, 0, pBuf, defaultSize);
+ if (errCode != DRV_OK)
+ {
+ memset(pBuf, 0, defaultSize);
+ }
+ memcpy(data, pBuf + offset, nDataSize);
+ free(pBuf);
+ }
+ break;
+ default :
+ DEBUG_ERR("[HMX_NVRAM_GetField] DI_ERR_INVALID_PARAM field(%d)-%s error(%08X) : HMX_NVRAM_Write\n", field, szFileName, errCode);
+ return 2;
+ }
+
+ return errCode;
+}
+
+DRV_Error HMX_NVRAM_SetField(NVRAM_FIELD_T field, unsigned int offset, void *data, int nDataSize)
+{
+ DRV_Error errCode = DRV_ERR;
+ unsigned char szFileName[MAX_NVRAM_FILENAME_LENGTH];
+ HMX_NVRAM_PARTITION_E partition;
+ int nvramHandle;
+ unsigned int defaultSize;
+ unsigned char *pBuf;
+ unsigned int systemId;
+
+ if( data == NULL || field == NVRAM_FIELD_DUMMY )
+ {
+ return 2;
+ }
+
+ pBuf = malloc(nDataSize);
+ if (pBuf == NULL)
+ {
+ return 5;
+ }
+
+ errCode = HMX_NVRAM_GetField(field, offset, pBuf, nDataSize);
+ if (errCode == DRV_OK)
+ {
+ if (memcmp(pBuf, data, nDataSize) == 0)
+ {
+ free(pBuf);
+ return 0;
+ }
+ }
+ free(pBuf);
+
+ errCode = drv_NVRAM_GetFieldInfo(field, &partition, szFileName, &defaultSize);
+ if (errCode != DRV_OK)
+ {
+ DEBUG_ERR("[HMX_NVRAM_SetField] error(%08X) : HMX_NVRAM_GetFieldInfo, field (%d)\n", errCode, field);
+ return errCode;
+ }
+
+ switch (partition)
+ {
+ case HMX_NVRAM_PARTITION_W_RAWFS :
+ errCode = DRV_NANDFLASH_GetNvramHandle(&nvramHandle);
+ if (errCode != DRV_OK)
+ {
+ return errCode;
+ }
+
+ errCode = DRV_FLASH_Write(s_nvram_offset[HMX_NVRAM_PARTITION_W_RAWFS] + offset, data, nDataSize);
+ if (errCode != DRV_OK)
+ {
+ DEBUG_ERR("[HMX_NVRAM_SetField] field(%d)-%s error(%08X) : HMX_NVRAM_Write\n", field, szFileName, errCode);
+ return errCode;
+ }
+ break;
+ case HMX_NVRAM_PARTITION_RO :
+ case HMX_NVRAM_PARTITION_RW :
+ if (defaultSize == 0)
+ {
+ if (field == NVRAM_FIELD_SYSTEM_ID && errCode == 0)
+ {
+ systemId = NVRAM_SWAP32((unsigned int)*(unsigned int*)data);
+ data = (void*)&systemId;
+ }
+ errCode = HMX_NVRAM_Write(partition, szFileName, 0, data, nDataSize);
+ if (errCode != DRV_OK)
+ {
+ DEBUG_ERR("[HMX_NVRAM_SetField] field(%d)-%s error(%08X) : HMX_NVRAM_Write\n", field, szFileName, errCode);
+ return errCode;
+ }
+ }
+ else
+ {
+ unsigned char *pBuf;
+
+ pBuf = malloc(defaultSize);
+ if (pBuf == NULL)
+ {
+ DEBUG_ERR("[HMX_NVRAM_SetField] malloc\n");
+ return 3;
+ }
+ errCode = HMX_NVRAM_Read(partition, szFileName, 0, pBuf, defaultSize);
+ if (errCode != DRV_OK)
+ {
+ memset(pBuf, 0, defaultSize);
+ }
+ memcpy(pBuf + offset, data, nDataSize);
+
+ errCode = HMX_NVRAM_Write(partition, szFileName, 0, pBuf, defaultSize);
+ free(pBuf);
+ if (errCode != DRV_OK)
+ {
+ DEBUG_ERR("[HMX_NVRAM_SetField] field(%d)-%s error(%08X) : HMX_NVRAM_Write\n", field, szFileName, errCode);
+ return errCode;
+ }
+ }
+ break;
+ default :
+ DEBUG_ERR("[HMX_NVRAM_SetField] DI_ERR_INVALID_PARAM field(%d)-%s error(%08X) : HMX_NVRAM_Write\n", field, szFileName, errCode);
+ return 1;
+ }
+
+ return errCode;
+}
+
+DRV_Error HMX_NVRAM_GetLength(NVRAM_FIELD_T field, int *pLen)
+{
+ DRV_Error errCode = DRV_ERR;
+ unsigned char szFileName[MAX_NVRAM_FILENAME_LENGTH];
+ HMX_NVRAM_PARTITION_E partition;
+ int nvramHandle;
+ unsigned int defaultSize;
+ unsigned char *pBuf;
+
+ if( pLen == NULL)
+ {
+ return 2;
+ }
+
+ *pLen = 0;
+
+ errCode = drv_NVRAM_GetFieldInfo(field, &partition, szFileName, &defaultSize);
+ if (errCode != DRV_OK)
+ {
+ DEBUG_ERR("[HMX_NVRAM_GetLength] error(%08X) : HMX_NVRAM_GetFieldInfo, field (%d)\n", errCode, field);
+ return errCode;
+ }
+
+ errCode = drv_NVRAM_GetLength(partition, szFileName, pLen);
+
+ return DRV_OK;
+}
+
+DRV_Error HMX_NVRAM_Remove(HMX_NVRAM_PARTITION_E partition, unsigned char *pName)
+{
+ int result;
+
+ SEM_Get(s_nvramSema);
+ result = drv_NVRAM_Delete(partition, pName);
+ if (result == 0)
+ {
+ result = drv_NVRAM_Save(partition);
+ }
+ SEM_Release(s_nvramSema);
+ return result;
+}
+
+DRV_Error HMX_NVRAM_Dump(unsigned char* pucBuffer, unsigned int uiLen, unsigned int uiAlign)
+{
+ unsigned int uiIndex;
+ unsigned int skip;
+
+ skip = 1;
+ for (uiIndex=0 ; uiIndex<uiLen ; uiIndex++)
+ {
+ if (uiAlign!=0 && (uiIndex%uiAlign)==0)
+ {
+ if (skip == 0)
+ {
+ printf("\n");
+ }
+ else
+ skip = 0;
+ }
+ printf("%02X ", *(pucBuffer+uiIndex));
+ }
+ printf("\n");
+ return DRV_OK;
+}
+
+DRV_Error HMX_NVRAM_Dir(void)
+{
+ char name[80];
+ char *value;
+ int nameLen, valueLen;
+ int idx;
+
+ value = malloc(MAX_DATA_LEN);
+ if (value == NULL)
+ {
+ return DRV_ERR_OUTOFMEMORY;
+ }
+
+ SEM_Get(s_nvramSema);
+
+ printf("ROM Name Value\n");
+ printf("-------------------- --------------------------------------------------\n");
+
+ for (idx=0;;idx++)
+ {
+ if (drv_NVRAM_ScanDir(HMX_NVRAM_PARTITION_RO, idx, (unsigned char*)name, (unsigned int*)&nameLen, (unsigned char*)value, (unsigned int*)&valueLen) != DRV_OK)
+ break;
+ printf("%20s ", name);
+ (void)HMX_NVRAM_Dump((unsigned char*)value, valueLen, 16);
+ }
+ printf("-------------------- --------------------------------------------------\n");
+
+ printf("\n");
+
+ printf("Variable Name Value\n");
+ printf("-------------------- --------------------------------------------------\n");
+
+ for (idx=0;;idx++)
+ {
+ if (drv_NVRAM_ScanDir(HMX_NVRAM_PARTITION_RW, idx, (unsigned char*)name, (unsigned int*)&nameLen, (unsigned char*)value, (unsigned int*)&valueLen) != DRV_OK)
+ break;
+ printf("%20s ", name);
+ (void)HMX_NVRAM_Dump((unsigned char*)value, valueLen, 16);
+ }
+ printf("-------------------- --------------------------------------------------\n");
+
+ free(value);
+
+ SEM_Release(s_nvramSema);
+ return DRV_OK;
+}
+
+/*@}*/
diff --git a/libupgrade/hmx_upgrade_nvram.h b/libupgrade/hmx_upgrade_nvram.h
new file mode 100644
index 0000000..242acd6
--- /dev/null
+++ b/libupgrade/hmx_upgrade_nvram.h
@@ -0,0 +1,337 @@
+/*******************************************************************/
+/************************* File Description ************************/
+/*******************************************************************/
+/* File Name: $Workfile: hmx_uprade_nvram.h $
+ * Version: $Revision: 1.0 $
+ * Original Author: Yang Hyun Uk $
+ * Current Author: $Author: huyang@humaxdigital.com $
+ * Date: $Date: 2011.11.07
+ * File Description: Upgrade APIs
+ * Module:
+ * Remarks:
+ */
+
+
+/**
+ * @author Hyunuk Yang(huyang@humaxdigital.com)
+ * @date 07 Nov 2011
+ */
+
+/**
+ * @note
+ * Copyright (C) 2011 Humax Corporation. All Rights Reserved. <br>
+ * This software is the confidential and proprietary information
+ * of Humax Corporation. You may not use or distribute this software
+ * except in compliance with the terms and conditions of any applicable license
+ * agreement in writing between Humax Corporation and you.
+ */
+
+ /*@{*/
+
+/**
+ * @file hmx_upgrade_nvram.h
+ */
+
+/*******************************************************************/
+/**************************** Header Files**************************/
+/*******************************************************************/
+/* Start Including Header Files */
+/* End Including Headers*/
+
+/*******************************************************************/
+/************************ Extern variables *************************/
+/*******************************************************************/
+/* Start Extern variablee */
+
+/* End Extern variable */
+
+
+/*******************************************************************/
+/************************ Macro Definition *************************/
+/*******************************************************************/
+/* Start Macro definition */
+
+/* End Macro definition */
+
+/*******************************************************************/
+/****************************** typedef ****************************/
+/*******************************************************************/
+/* Start typedef */
+
+typedef enum
+{
+ NVRAM_OSD_ON = 0,
+ NVRAM_OSD_OFF
+}NVRAM_OSD_DISPLAY_E;
+
+typedef enum
+{
+ NVRAM_FRONTPANEL_DISPLAY_ON = 0,
+ NVRAM_FRONTPANEL_DISPLAY_OFF
+}NVRAM_FRONTPANEL_DISPLAY_E;
+
+typedef enum
+{
+ NVRAM_ASPECT_RATIO_4_3 = 0,
+ NVRAM_ASPECT_RATIO_16_9
+}NVRAM_ASPECT_RATIO_E;
+
+typedef enum
+{
+ NVRAM_OTA_SSU = 1,
+ NVRAM_OTA_DTG = 2,
+ NVRAM_OTA_HUMAX = 3,
+ NVRAM_OTA_NORDIG = 4,
+ NVRAM_OTA_FILE = 5,
+ NVRAM_OTA_SKYD = 6,
+ NVRAM_OTA_MAX
+}NVRAM_OTA_TYPE_E;
+
+
+typedef enum
+{
+ NVRAM_OTA_CHANNEL_SAT = 1,
+ NVRAM_OTA_CHANNEL_CAB = 2,
+ NVRAM_OTA_CHANNEL_TER = 3,
+ NVRAM_OTA_CHANNEL_FLASH = 4,
+ NVRAM_OTA_CHANNEL_FTP = 5
+}NVRAM_OTA_CHANNEL_E;
+
+typedef enum
+{
+ NVRAM_RESOLUTION_Unknown =0x00000000,
+ NVRAM_RESOLUTION_720x240P =0x00000001,
+ NVRAM_RESOLUTION_2880x240P =0x00000002,
+ NVRAM_RESOLUTION_640x480P =0x00000004,
+ NVRAM_RESOLUTION_720x480I =0x00000008,
+ NVRAM_RESOLUTION_720x480P =0x00000010,
+ NVRAM_RESOLUTION_1440x480P =0x00000020,
+ NVRAM_RESOLUTION_2880x480I =0x00000040,
+ NVRAM_RESOLUTION_2880x480P =0x00000080,
+ NVRAM_RESOLUTION_720x288P =0x00000100,
+ NVRAM_RESOLUTION_2880x288P =0x00000200,
+ NVRAM_RESOLUTION_720x576I =0x00000400,
+ NVRAM_RESOLUTION_720x576P =0x00000800,
+ NVRAM_RESOLUTION_1440x576P =0x00001000,
+ NVRAM_RESOLUTION_2880x576I =0x00002000,
+ NVRAM_RESOLUTION_2880x576P =0x00004000,
+ NVRAM_RESOLUTION_1080x720P =0x00008000,
+ NVRAM_RESOLUTION_1280x720P =0x00010000,
+ NVRAM_RESOLUTION_1920x1080I =0x00020000,
+ NVRAM_RESOLUTION_1920x1080P =0x00040000,
+ NVRAM_RESOLUTION_DUMMY =0x000FFFFF
+} NVRAM_VIDEO_RESOLUTION_E;
+
+typedef enum
+{
+ NVRAM_HDMI_FIELD_RATE_Unknown =0x0000,
+ NVRAM_HDMI_FIELD_RATE_24HZ =0x0001,
+ NVRAM_HDMI_FIELD_RATE_25HZ =0x0002,
+ NVRAM_HDMI_FIELD_RATE_30HZ =0x0004,
+ NVRAM_HDMI_FIELD_RATE_50HZ =0x0008,
+ NVRAM_HDMI_FIELD_RATE_60HZ =0x0010,
+ NVRAM_HDMI_FIELD_RATE_100HZ =0x0020,
+ NVRAM_HDMI_FIELD_RATE_120HZ =0x0040,
+ NVRAM_HDMI_FIELD_RATE_200HZ =0x0080,
+ NVRAM_HDMI_FIELD_RATE_240HZ =0x0100,
+ NVRAM_HDMI_FIELD_RATE_DUMMY =0xFFFF
+} NVRAM_HDMI_VIDEO_FIELD_RATE_E;
+
+
+typedef enum
+{
+ NVRAM_HDMI_VIDEO_AR_eNoData = 0,
+ NVRAM_HDMI_VIDEO_AR_e4_3,
+ NVRAM_HDMI_VIDEO_AR_e16_9
+}NVRAM_HDMI_VIDEO_AR_E;
+
+
+typedef enum
+{
+ NVRAM_SCART_OUTPUT_CVBS=3,
+ NVRAM_SCART_OUTPUT_RGB,
+ NVRAM_SCART_OUTPUT_SVIDEO,
+
+ NVRAM_SCART_MAX
+} NVRAM_SCART_SETTING_VALUE;
+
+typedef enum tagNVRAM_FIELD
+{
+ NVRAM_FIELD_SYSTEM_ID = 0, // unsigned int // 4 // System Id
+ NVRAM_FIELD_SFLASH,
+ NVRAM_FIELD_SERIAL_NO,
+ NVRAM_FIELD_MAC_ADDR,
+ NVRAM_FIELD_HDCP_KEY,
+ NVRAM_FIELD_DTCP_KEY,
+ NVRAM_FIELD_CI_PLUS_KEY,
+ NVRAM_FIELD_PARING_DATA,
+ NVRAM_FIELD_PRIVATE,
+ NVRAM_FIELD_CSC_KEY,
+ NVRAM_FIELD_CM_SERIAL_NO,
+ NVRAM_FIELD_CM_MAC_ADDR,
+ NVRAM_FIELD_CM_MAC_ADDR_ANOTHER,
+ NVRAM_FIELD_IRDETO_BBCB,
+
+ NVRAM_FIELD_OTA_TYPE1 = 0x100, // NVRAM_OTA_TYPE_E
+ NVRAM_FIELD_OTA_TYPE2, // NVRAM_OTA_TYPE_E
+ NVRAM_FIELD_OTA_TYPE3, // NVRAM_OTA_TYPE_E
+ NVRAM_FIELD_CH_TYPE1, // NVRAM_OTA_CHANNEL_E
+ NVRAM_FIELD_CH_TYPE2, // NVRAM_OTA_CHANNEL_E
+ NVRAM_FIELD_CH_TYPE3, // NVRAM_OTA_CHANNEL_E
+ NVRAM_FIELD_OTA_FLAG1, // NVRAM_OTA_FLAG_E
+ NVRAM_FIELD_OTA_FLAG2, // NVRAM_OTA_FLAG_E
+ NVRAM_FIELD_OTA_FLAG3, // NVRAM_OTA_FLAG_E
+ NVRAM_FIELD_TUNER_ID1, // Tuner Id
+ NVRAM_FIELD_TUNER_ID2, // Tuner Id
+ NVRAM_FIELD_TUNER_ID3, // Tuner Id
+ NVRAM_FIELD_ANTENA_POWER1, // External Antena Power for Ter, 0:Off/1:On
+ NVRAM_FIELD_ANTENA_POWER2, // External Antena Power for Ter, 0:Off/1:On
+ NVRAM_FIELD_ANTENA_POWER3, // External Antena Power for Ter, 0:Off/1:On
+ NVRAM_FIELD_ES_PID1, // Element Stream PID for OTA
+ NVRAM_FIELD_ES_PID2, // Element Stream PID for OTA
+ NVRAM_FIELD_ES_PID3, // Element Stream PID for OTA
+ NVRAM_FIELD_TRANSACTION_ID1, // Transaction Id for Nordic OTA
+ NVRAM_FIELD_TRANSACTION_ID2, // Transaction Id for Nordic OTA
+ NVRAM_FIELD_TRANSACTION_ID3, // Transaction Id for Nordic OTA
+ NVRAM_FIELD_CH_INFO_S, // DI_CHANNEL_PARAM
+ NVRAM_FIELD_CH_INFO_T, // DI_CHANNEL_PARAM
+ NVRAM_FIELD_CH_INFO_C, // DI_CHANNEL_PARAM
+ NVRAM_FIELD_NET_PORTAL_IP, // portal ip address
+ NVRAM_FIELD_NET_DOWN_PATH, // Network Download Path
+ NVRAM_FIELD_NET_DEVICE_ID, // ethernet device id 0 = eth0
+ NVRAM_FIELD_NET_IP_CONFIG, // DHCP/Manual
+ NVRAM_FIELD_NET_IP_SETTING, // Manual IP setting
+ NVRAM_FIELD_OTA_FTP_INFO, // NVRAM_FTP_OTA_SETTING_T
+ NVRAM_FIELD_FILE_SIZE, // file size of backgrould ota
+
+ NVRAM_FIELD_LOADER_VERSION, // Version of boot Loader
+ NVRAM_FIELD_APP_VERSION, // Version number of Application
+ NVRAM_FIELD_OTALDR_VERSION, // Version of OTA Loader
+ NVRAM_FIELD_CUR_OTAIMAGE_VERSION, // Version number of OTA image
+ NVRAM_FIELD_LOADER_VER,
+ NVRAM_FIELD_APP_VER,
+
+ NVRAM_FIELD_LANGUAGE, // OSD language code in ISO 639 code
+ NVRAM_FIELD_COUNTRY_CODE, // unsigned char a[3]
+ NVRAM_FIELD_TV_STANDARD, // DI_VIDEO_SD_STANDARD
+ NVRAM_FIELD_SCART_RGB, // NVRAM_SCART_SETTING_VALUE
+ NVRAM_FIELD_HD_RESOULTION, // NVRAM_VIDEO_RESOLUTION_E
+ NVRAM_FIELD_FIELD_RATE, // NVRAM_HDMI_VIDEO_FIELD_RATE_E
+ NVRAM_FIELD_OAD_VERSION, // for MHEG ???
+ NVRAM_FIELD_RCU_CUSTOM_CODE, // for RCU custom code
+ NVRAM_FIELD_RCU_CUSTOM_CODE2, // for alternative RCU custom code
+ NVRAM_FIELD_PANEL_DISPLAY, // DI_OTA_PANELDISPLAY_t
+ NVRAM_FIELD_PANEL_DIMMING, // unsigned char
+ NVRAM_FIELD_OSD_DISPLAY, // NVRAM_OSD_DISPLAY_E
+ NVRAM_FIELD_START_BANK_FLAG, // µÎ °³ÀÇ bankÁß ¾îµð·Î ºÎÆà ÇÒ Áö °áÁ¤
+ NVRAM_FIELD_CHECK_USB, // ºÎÆà ½Ã USB ¸¶¿îÆ®Çؼ hdf¸¦ °Ë»çÇÒÁö ¸»Áö °áÁ¤
+ NVRAM_FIELD_CHECK_USB_COUNT, // À§ µ¿ÀÛ ½ÇÆÐ ½Ã ¸î ¹ø Àç ½Ãµµ ÇÒÁö count¸¦ ÀúÀå
+ NVRAM_FIELD_ASPECT_RATIO, // NVRAM_ASPECT_RATIO_E
+ NVRAM_FIELD_USAGE_ID, // for UPC OTA
+ NVRAM_FIELD_BIN8K, // for eeprom emulation
+ NVRAM_FIELD_IRDETO_CPCB, // for IRDETO CPCB
+ NVRAM_FIELD_IRDETO_CPCB_ENCRYPTED, // for IRDETO CPCB (encrypted)
+
+ NVRAM_FIELD_ACTIVATED_KERNEL_NUM, // ACTIVATED_KERNEL_NUM
+ NVRAM_FIELD_ACTIVATED_ROOTFS_NUM, // ACTIVATED_ROOTFS_NUM
+ NVRAM_FIELD_MTD_TYPE_FOR_KERNEL, // MTD_TYPE_FOR_KERNEL
+ NVRAM_FIELD_TYPE_OF_FILESYSTEM, // TYPE_OF_FILESYSTEM
+ NVRAM_FIELD_L_TYPE_OF_FILESYSTEM, // Length TYPE_OF_FILESYSTEM
+ NVRAM_FIELD_NAME_OF_BOARD, // NAME_OF_BOARD
+ NVRAM_FIELD_L_NAME_OF_BOARD, // Length NAME_OF_BOARD
+
+
+ NVRAM_FIELD_RAWFS = 0x1000,
+ NVRAM_FIELD_DUMMY = 0xFFFF
+} NVRAM_FIELD_T;
+
+typedef enum
+{
+ NVRAM_OTA_FLAG_NO_OTA = 0x00,
+ NVRAM_OTA_FLAG_DETECTED = 0x01,
+ NVRAM_OTA_FLAG_COMPLETED = 0x02,
+ NVRAM_OTA_FLAG_FORCE_UPGRADE = 0x04,
+ NVRAM_OTA_FLAG_NAGRA_RECOVERY = 0x08,
+ NVRAM_OTA_FLAG_DOWNLOADING = 0x10,
+ NVRAM_OTA_FLAG_WRITING = 0x20,
+ NVRAM_OTA_FLAG_ERROR = 0x80
+} NVRAM_OTA_FLAG_E;
+
+typedef struct NVRAM_NET_IP_SETTING_Tag
+{
+#define NET_ADDR_LENGTH 4
+ unsigned char ip[NET_ADDR_LENGTH];
+ unsigned char mask[NET_ADDR_LENGTH];
+ unsigned char gateway[NET_ADDR_LENGTH];
+ unsigned char dns[NET_ADDR_LENGTH];
+} NVRAM_NET_IP_SETTING_T;
+
+typedef struct NVRAM_FTP_OTA_SETTING_Tag
+{
+#define NVRAM_FTP_USER_LENGTH 20
+#define NVRAM_FTP_PASSWD_LENGTH 20
+#define NVRAM_FTP_DIR_PATH_LENGTH 200
+#define NVRAM_FTP_FILE_NAME_LENGTH 50
+ unsigned char aServerIp[NET_ADDR_LENGTH];
+ unsigned char aUserName[NVRAM_FTP_USER_LENGTH];
+ unsigned char aPasswd[NVRAM_FTP_PASSWD_LENGTH];
+ unsigned char aDirPath[NVRAM_FTP_DIR_PATH_LENGTH];
+ unsigned char aFileName[NVRAM_FTP_FILE_NAME_LENGTH];
+} NVRAM_FTP_OTA_SETTING_T;
+
+typedef enum
+{
+ NVRAM_IP_DHCP = 0,
+ NVRAM_IP_MANUAL
+} NVRAM_NET_IP_CONFIG_E;
+
+/* Start global function prototypes */
+typedef enum HMX_NVRAM_PARTITION_e
+{
+ HMX_NVRAM_PARTITION_RO,
+ HMX_NVRAM_PARTITION_RW,
+ HMX_NVRAM_PARTITION_W_RAWFS,
+ HMX_NVRAM_PARTITION_MAX
+}HMX_NVRAM_PARTITION_E;
+
+
+typedef enum
+{
+ DRV_OK = 0,
+ DRV_ERR,
+
+ DRV_ERR_INVALID_PARAMETER,
+ DRV_ERR_INITIALIZATION,
+ DRV_ERR_EVENT_INITIALIZATION,
+ DRV_ERR_OUTOFMEMORY,
+ DRV_ERR_EXTERNAL_ERROR
+
+}DRV_Error;
+
+/* End typedef */
+
+
+/*******************************************************************/
+/******************** global function prototype ********************/
+/*******************************************************************/
+extern int HMX_UPGRADE_NVRAM_Write(unsigned long offset, unsigned char * data, unsigned int size );
+extern int HMX_UPGRADE_NVRAM_Read(unsigned long offset, unsigned char * data, unsigned int size );
+
+
+/*******************************************************************/
+/******************** global function prototype ********************/
+/*******************************************************************/
+DRV_Error HMX_NVRAM_Init(void);
+DRV_Error HMX_NVRAM_Write(HMX_NVRAM_PARTITION_E partition, unsigned char *pName, unsigned int offset, unsigned char *pValue, unsigned int ulSize);
+DRV_Error HMX_NVRAM_Read(HMX_NVRAM_PARTITION_E partition, unsigned char *pName, unsigned int offset, unsigned char *pValue, unsigned int ulSize);
+DRV_Error HMX_NVRAM_GetField(NVRAM_FIELD_T field, unsigned int offset, void *data, int nDataSize);
+DRV_Error HMX_NVRAM_SetField(NVRAM_FIELD_T field, unsigned int offset, void *data, int nDataSize);
+DRV_Error HMX_NVRAM_GetLength(NVRAM_FIELD_T field, int *pLen);
+DRV_Error HMX_NVRAM_Remove(HMX_NVRAM_PARTITION_E partition, unsigned char *pName);
+DRV_Error HMX_NVRAM_Dir(void);
+
+
+/* End global function prototypes */
+
+
+/*@}*/
diff --git a/libupgrade/hmx_upgrade_system.c b/libupgrade/hmx_upgrade_system.c
new file mode 100644
index 0000000..70442d7
--- /dev/null
+++ b/libupgrade/hmx_upgrade_system.c
@@ -0,0 +1,1557 @@
+/*******************************************************************/
+/************************* File Description ************************/
+/*******************************************************************/
+/* File Name: $Workfile: hmx_uprade_system.c $
+ * Version: $Revision: 1.0 $
+ * Original Author: Yang Hyun Uk $
+ * Current Author: $Author: huyang@humaxdigital.com $
+ * Date: $Date: 2011.09.30
+ * File Description: Humax Upgrade APIs
+ * Module:
+ * Remarks:
+ */
+
+/**
+ * @defgroup UPGRADE_SYSTEM System APIs for Upgrade Module
+ * @ingroup UPGRADE
+ */
+
+/**
+ * @author Hyunuk Yang(huyang@humaxdigital.com)
+ * @date 30 Sept 2011
+ */
+
+/**
+ * @note
+ * Copyright (C) 2011 Humax Corporation. All Rights Reserved. <br>
+ * This software is the confidential and proprietary information
+ * of Humax Corporation. You may not use or distribute this software
+ * except in compliance with the terms and conditions of any applicable license
+ * agreement in writing between Humax Corporation and you.
+ */
+
+ /*@{*/
+
+/**
+ * @file hmx_upgrade_system.c
+ */
+
+/*******************************************************************/
+/**************************** Header Files *************************/
+/*******************************************************************/
+/* Start Including Header Files */
+#include "hmx_upgrade_system.h"
+/* End Including Headers */
+
+
+/*******************************************************************/
+/****************************** define *****************************/
+/*******************************************************************/
+
+#ifdef TASK_DEBUG
+#define PrintDebug(fmt, ...) printf (fmt, ## __VA_ARGS__)
+#define PrintError(fmt, ...) printf (fmt, ## __VA_ARGS__)
+#define PrintEnter(...) printf("(+)%s\n", __FUNCTION__)
+#define PrintExit(...) printf("(-)%s\n", __FUNCTION__)
+#else
+#define PrintDebug(fmt, ...) while (0) ((int (*)(char *, ...)) 0)
+#define PrintError(fmt, ...) printf (fmt, ## __VA_ARGS__)
+#define PrintEnter(...) while (0) ((int (*)(char *, ...)) 0)
+#define PrintExit(...) while (0) ((int (*)(char *, ...)) 0)
+#endif
+
+
+#define list_size(list) ((list)->curr_msg_count_)
+
+#define list_bitmap_size(list, i) ((list)->bitmap_count[(i)])
+
+#define list_head(list, i) ((list)->head[i])
+
+#define list_tail(list, i) ((list)->tail[i])
+
+#define list_is_head(list, element) ((element) == (list)->head ? 1 : 0)
+
+#define list_is_tail(element) ((element)->next == NULL ? 1 : 0)
+
+#define list_data(element) ((element)->data)
+
+#define list_next(element) ((element)->next)
+
+#define HAPPY(a) (void)(a)
+
+/* End #define */
+
+/*******************************************************************/
+/****************************** typedef ****************************/
+/*******************************************************************/
+/* Start typedef */
+/* End typedef */
+
+
+/*******************************************************************/
+/************************ global variables *************************/
+/*******************************************************************/
+/* Start global variable */
+
+/* End global variable */
+
+
+/*******************************************************************/
+/************************ static variables *************************/
+/*******************************************************************/
+/* Start static variable */
+/* End static variable */
+
+
+/*******************************************************************/
+/************************ static funtions **************************/
+/*******************************************************************/
+
+static int P_MSG_Check(struct HMX_MSG_queue *q, unsigned long q_id);
+
+
+/*
+ list_find_highest_priority_bitmap
+ bitmap¿¡¼ °¡Àå ³ôÀº ¿ì¼±¼øÀ§¸¦ ã´Â´Ù.
+*/
+unsigned long list_find_highest_priority_bitmap(struct HMX_MSG_queue *list)
+{
+ int i;
+
+ for(i=MSG_PRIORITY_MAX-1; i>=0; i--)
+ {
+ if(list->bitmap[i] == 1)
+ return i;
+ }
+
+ return 0;
+}
+
+
+
+/*
+ print_list
+ HMX_MSG_queue ±¸Á¶Ã¼ Àüü¸¦ PrintÇÑ´Ù.
+*/
+void print_list(const struct HMX_MSG_queue *list)
+{
+ struct HMX_MSG_element *element;
+ int *data, i, count;
+
+ fprintf(stdout, "Msg Queue Current total size is %ld\n", list_size(list));
+
+ for(count=0; count<MSG_PRIORITY_MAX; count++)
+ {
+ i = 0;
+
+ if( list->bitmap[count] != 0)
+ {
+ element = list_head(list, count);
+
+ while (1)
+ {
+ data = list_data(element);
+ fprintf(stdout, "priority[%d] : qlist[%03d]=%03d\n", count, i, *data);
+
+ i++;
+
+ if (list_is_tail(element))
+ break;
+ else
+ element = list_next(element);
+ }
+ }
+ }
+}
+
+
+
+/*
+ list_set_bitmap
+ ¿ì¼±¼øÀ§¿¡ ÇØ´çÇÏ´Â ºñÆ®¸ÊÀ» set ÇÑ´Ù.
+*/
+void list_set_bitmap(struct HMX_MSG_queue *list, unsigned long prio)
+{
+ list->bitmap[prio] = 1;
+}
+
+
+
+/*
+ list_clear_bitmap
+ ¿ì¼±¼øÀ§¿¡ ÇØ´çÇÏ´Â ºñÆ®¸ÊÀ» clear ÇÑ´Ù.
+*/
+void list_clear_bitmap(struct HMX_MSG_queue *list, unsigned long prio)
+{
+ list->bitmap[prio] = 0;
+}
+
+
+
+
+
+
+
+/*
+ list_bitmap_count_increase
+ ÇØ´çÇÏ´Â ¿ì¼±¼øÀ§ÀÇ bitmap Count¸¦ Áõ°¡ ½ÃŲ´Ù.
+*/
+void list_bitmap_count_increase(struct HMX_MSG_queue *list, unsigned long prio)
+{
+ list->bitmap_count[prio]++;
+}
+
+
+
+/*
+ list_bitmap_count_decrease
+ ÇØ´çÇÏ´Â ¿ì¼±¼øÀ§ÀÇ bitmap Count¸¦ °¨¼Ò ½ÃŲ´Ù.
+*/
+void list_bitmap_count_decrease(struct HMX_MSG_queue *list, unsigned long prio)
+{
+ list->bitmap_count[prio]--;
+}
+
+
+/*
+ list_mapping_task_priority_to_msgq
+ ŽºÅ© ¿ì¼±¼øÀ§¸¦ ±âÁØÀ¸·Î ¸Þ¼¼ÁöÅ¥ ¿ì¼±¼øÀ§¸¦ °áÁ¤ÇÑ´Ù.
+*/
+int list_find_msg_q_priority_from_task_priority(unsigned long *prio)
+{
+ struct sched_param param;
+ int policy = 0;
+ int rc;
+
+ rc = pthread_getschedparam( pthread_self(), &policy, ¶m);
+ if(rc != HMX_OK)
+ {
+ *prio = MSG_PRIORITY0;
+ return HMX_OK;
+ }
+ PrintDebug("policy = %d\n", policy);
+ PrintDebug("param.sched_priority = %d\n", param.sched_priority);
+
+ switch(param.sched_priority)
+ {
+ case USER_PRIORITY0:
+ *prio = MSG_PRIORITY0;
+ break;
+ case USER_PRIORITY1:
+ *prio = MSG_PRIORITY1;
+ break;
+ case USER_PRIORITY2:
+ *prio = MSG_PRIORITY2;
+ break;
+ case USER_PRIORITY3:
+ *prio = MSG_PRIORITY3;
+ break;
+ case USER_PRIORITY4:
+ *prio = MSG_PRIORITY4;
+ break;
+ case USER_PRIORITY5:
+ *prio = MSG_PRIORITY5;
+ break;
+ case USER_PRIORITY6:
+ *prio = MSG_PRIORITY6;
+ break;
+ case USER_PRIORITY7:
+ *prio = MSG_PRIORITY7;
+ break;
+ case USER_PRIORITY8:
+ *prio = MSG_PRIORITY8;
+ break;
+ case USER_PRIORITY9:
+ *prio = MSG_PRIORITY9;
+ break;
+ case USER_PRIORITY10:
+ *prio = MSG_PRIORITY10;
+ break;
+ case USER_PRIORITY11:
+ *prio = MSG_PRIORITY11;
+ break;
+ case USER_PRIORITY12:
+ *prio = MSG_PRIORITY12;
+ break;
+ case USER_PRIORITY13:
+ *prio = MSG_PRIORITY13;
+ break;
+ case USER_PRIORITY14:
+ *prio = MSG_PRIORITY14;
+ break;
+ case USER_PRIORITY15:
+ *prio = MSG_PRIORITY15;
+ break;
+ default:
+ *prio = MSG_PRIORITY15;
+ break;
+ }
+
+ return HMX_OK;
+}
+
+
+/*
+ q_insert_temp_tail_element
+ temp Qeue¿¡ element¸¦ ¿¬°á ÇÑ´Ù.
+*/
+void q_insert_temp_tail_element(struct HMX_MSG_queue *q, struct HMX_MSG_element *element)
+{
+ if(q->temp_tail == NULL)
+ {
+ q->temp_head = element;
+ element->next = NULL;
+ element->prev = NULL;
+ q->temp_tail = element;
+ }
+ else
+ {
+ q->temp_tail->next = element;
+ element->next = NULL;
+ element->prev = q->temp_tail;
+ q->temp_tail = element;
+ }
+}
+
+/*
+ q_remove_temp_tail_element
+ temp Qeue¿¡¼ ¸¶Áö¸· element¸¦ Á¦°ÅÇÏ¿© ³Ñ°ÜÁØ´Ù.
+*/
+void q_remove_temp_tail_element(struct HMX_MSG_queue *q, struct HMX_MSG_element **element)
+{
+ PrintEnter();
+
+ *element = q->temp_tail;
+
+ if(q->temp_head->next == NULL) //element 1°³ ³²Àº °æ¿ì.
+ {
+ q->temp_head = NULL;
+ q->temp_tail = NULL;
+ }
+ else
+ {
+ q->temp_tail->prev->next = NULL;
+ q->temp_tail = q->temp_tail->prev;
+ }
+ PrintExit();
+}
+
+/*
+ q_destory_temp_tail
+ temp QeueÀÇ element memory¸¦ ¼Ò¸ê½ÃŲ´Ù.
+*/
+void q_destory_temp_tail(struct HMX_MSG_queue *q)
+{
+ struct HMX_MSG_element *q_element;
+
+ PrintEnter();
+
+ do
+ {
+ q_element = q->temp_tail;
+ q->temp_tail = q->temp_tail->prev;
+
+
+ } while(q->temp_tail != NULL);
+ if (q->pPool)
+ {
+ free(q->pPool);
+ q->pPool = NULL;
+ }
+ if (q->pDataPool)
+ {
+ free(q->pDataPool);
+ q->pDataPool = NULL;
+ }
+
+ PrintExit();
+}
+
+
+/*
+ list_rem_next
+ element¿¡¼ data¸¦ »èÁ¦ÇÑ´Ù.
+*/
+int list_rem_next(struct HMX_MSG_queue *list, void *data, unsigned long size, unsigned char timeoutflag, struct timespec *timeo)
+{
+ struct HMX_MSG_element *old_element;
+ unsigned long prio;
+ int rc = 0;
+
+ PrintEnter();
+
+ list->reader_count_++;
+
+ if ((list_size(list) == 0 || list->reader_count_ > 1) && 0 == rc)
+ {
+ if(TRUE == timeoutflag)
+ {
+ rc = pthread_cond_timedwait(&list->q_not_empty_, &list->q_lock_, timeo);
+ }
+ else
+ {
+ rc = pthread_cond_wait(&list->q_not_empty_, &list->q_lock_);
+ }
+ }
+
+ list->reader_count_--;
+
+ if(rc != 0)
+ {
+ PrintDebug("%s : rc[%d] !!\n", __FUNCTION__, rc);
+ return rc;
+ }
+
+ prio = list_find_highest_priority_bitmap(list);
+ PrintDebug("list_find_highest_priority_bitmap : prio = %d\n", prio);
+
+ memcpy(data, list->head[prio]->data, size);
+ old_element = list->head[prio];
+ if(NULL == list->head[prio]->next)
+ {
+ list->head[prio] = NULL;
+ list->tail[prio] = NULL;
+ }
+ else
+ {
+ list->head[prio] = list->head[prio]->next;
+ }
+
+ q_insert_temp_tail_element(list, old_element);
+ list->curr_msg_count_--;
+ list_bitmap_count_decrease(list, prio);
+
+ if(list->bitmap_count[prio] == 0)
+ list_clear_bitmap(list, prio);
+
+ if (list->writer_count_ > 0)
+ pthread_cond_signal(&list->q_not_full_);
+
+ PrintExit();
+
+ return rc;
+}
+
+
+static void *thread_func_(void *arg)
+{
+ struct HMX_TASK_arg *p = (struct HMX_TASK_arg *)arg;
+ int rc = 0;
+
+#if defined(CONFIG_DEBUG)
+ p->pid = getpid();
+ p->tid = (long int)syscall(4222);
+#endif
+
+ pthread_mutex_lock(&p->lock_);
+
+ while (p->start == 0 && 0 == rc) //wait signal
+ rc = pthread_cond_wait(&p->cond_, &p->lock_);
+
+ pthread_mutex_unlock(&p->lock_);
+
+#if defined(CONFIG_DEBUG)
+
+ p->thread_id = pthread_self();
+ PrintDebug("[%s] task started...\n", p->name);
+#endif
+
+ (*p->start_func_)(p->arg_);
+
+ return NULL;
+}
+
+
+/*
+ HMX_TASK_Create
+ ŽºÅ©¸¦ »ý¼ºÇÑ´Ù.
+*/
+int HMX_TASK_Create(void (*start_func)(void *), unsigned long prio,unsigned long stack_size, const char *name, void *arg, unsigned long *taskId, int IsJoinable)
+{
+ int rc;
+ struct HMX_TASK *task;
+ pthread_attr_t thread_attr;
+ struct sched_param schParam;
+ unsigned char *pucDstStackAddr = NULL;
+ unsigned char *pucTaskStack;
+
+ rc = pthread_attr_init (&thread_attr);
+ if (rc) {
+ return HMX_ERROR;
+ }
+
+ rc = pthread_attr_setschedpolicy (&thread_attr, HMX_TASK_PTHREAD_DEFAULT_PRIO);
+ if (rc) {
+ return HMX_ERROR;
+ }
+
+ pthread_attr_getschedparam(&thread_attr, &schParam);
+ schParam.sched_priority = prio;
+ rc = pthread_attr_setschedparam (&thread_attr, &schParam);
+ if (rc) {
+ return HMX_ERROR;
+ }
+
+ if (stack_size < HMX_TASK_PTHREAD_STACK_MIN)
+ stack_size = HMX_TASK_PTHREAD_STACK_MIN;
+
+ pucTaskStack = malloc(stack_size+HMX_TASK_STACK_OVERHEAD_SIZE+HMX_TASK_GUARD_SIZE);
+ if (pucTaskStack == NULL)
+ return HMX_ERROR;
+ memset(pucTaskStack, 0xA5, stack_size+HMX_TASK_STACK_OVERHEAD_SIZE+HMX_TASK_GUARD_SIZE );
+
+ PrintDebug("%s(%d) : pucTaskStack = %p, stack_size= %d\n", __FUNCTION__, __LINE__, pucTaskStack, stack_size);
+ rc = pthread_attr_setstack(&thread_attr, (void *)pucTaskStack, stack_size );
+ if (rc) {
+ return HMX_ERROR;
+ }
+
+ rc = pthread_attr_getstack(&thread_attr,(void *)&pucDstStackAddr, (size_t *)&stack_size );
+ if (rc) {
+ return HMX_ERROR;
+ }
+ PrintDebug("%s(%d) : pucDstStackAddr = %p, stack_size= %d\n", __FUNCTION__, __LINE__, pucDstStackAddr, stack_size);
+
+ if (IsJoinable == TRUE)
+ {
+ rc = pthread_attr_setdetachstate(&thread_attr, PTHREAD_CREATE_JOINABLE);
+ }
+ else if(IsJoinable == FALSE)
+ {
+ rc = pthread_attr_setdetachstate(&thread_attr, PTHREAD_CREATE_DETACHED);
+ }
+ else
+ {
+ PrintError("%s(%s) : IsJoinable Parameter Error!!\n", __func__, __LINE__);
+ return HMX_ERROR;
+ }
+
+ if (rc) {
+ PrintError ("%s(%d) : Failed to IsJoinable %s\n", __FUNCTION__, __LINE__, strerror (rc));
+ return HMX_ERROR;
+ }
+
+ if (task = (struct HMX_TASK *)malloc(sizeof(struct HMX_TASK)), NULL == task) {
+ *taskId = 0;
+ free(pucTaskStack);
+ return HMX_ERROR;
+ }
+
+ task->targ_.start_func_ = start_func;
+ task->targ_.arg_ = arg;
+ task->targ_.priority_ = prio;
+ task->targ_.stackSize_ = stack_size;
+ task->targ_.IsJoinable = IsJoinable;
+ task->targ_.pucTaskStack = (unsigned long *)pucTaskStack;
+ task->targ_.pulStackStartAddress = (unsigned long *)pucDstStackAddr;
+
+ pthread_mutex_init(&task->targ_.lock_, NULL);
+ pthread_cond_init(&task->targ_.cond_, NULL);
+ task->targ_.start = 0;
+
+ strncpy(task->targ_.name, name, sizeof(task->targ_.name)-1);
+
+ rc = pthread_create(&task->task_, &thread_attr, thread_func_, &task->targ_);
+ if (rc) {
+ free(pucTaskStack);
+ free(task);
+ *taskId = 0;
+ return HMX_ERROR;
+ }
+
+ *taskId = (unsigned long)task;
+
+#if defined(CONFIG_TASK_PRIORITY)
+ pthread_setschedparam(task->task_, HMX_TASK_PTHREAD_DEFAULT_PRIO, &schParam);
+#endif
+
+ pthread_attr_destroy(&thread_attr);
+ PrintDebug("%s(%d) : s_ucTaskCount = %d\n", __func__, __LINE__, s_ucTaskCount);
+ return HMX_OK;
+}
+
+int HMX_TASK_Start(unsigned long taskId)
+{
+ struct HMX_TASK *task = (struct HMX_TASK *)taskId;
+ PrintEnter();
+
+ if(NULL == task)
+ {
+ PrintError("%s(%d) : task is NULL!!\n", __func__, __LINE__);
+ return HMX_ERROR;
+ }
+
+ pthread_mutex_lock(&task->targ_.lock_);
+ if (task->targ_.start == 0) {
+ task->targ_.start = 1;
+ pthread_cond_signal(&task->targ_.cond_);
+ }
+ pthread_mutex_unlock(&task->targ_.lock_);
+ PrintExit();
+ return HMX_OK;
+}
+
+/*
+ HMX_TASK_Stop
+ Task¸¦ ¼öÇàµÈ ÀÌÈÄ¿¡ ÀÌ ÇÔ¼ö¸¦ È£ÃâÇصµ STOPÀº µÇÁö ¾Ê´Â´Ù.
+ ´ÜÁö count¸¸ 0À¸·Î ¸¸µç´Ù.
+*/
+int HMX_TASK_Stop(unsigned long taskId)
+{
+ struct HMX_TASK *task = (struct HMX_TASK *)taskId;
+
+ PrintEnter();
+
+ if (task == NULL) {
+ return HMX_OK;
+ }
+
+ pthread_mutex_lock(&task->targ_.lock_);
+ if (task->targ_.start != 0)
+ task->targ_.start = 0;
+ pthread_mutex_unlock(&task->targ_.lock_);
+
+ return HMX_OK;
+}
+
+/*
+ sleep
+ ŽºÅ©¸¦ ÀáÀç¿î´Ù.
+*/
+int HMX_Sleep(unsigned long ultime)
+{
+ struct timespec delay;
+ struct timespec rem;
+ int rc;
+
+ if (ultime != 0)
+ {
+ HMX_TASK_CheckCallback();
+ }
+ delay.tv_sec = ultime / 1000;
+ delay.tv_nsec = (ultime % 1000) * 1000000;
+
+ for (;;) {
+ rc = nanosleep(&delay, &rem);
+ if (0 != rc) {
+ if (EINTR == errno) {
+ delay = rem;
+ continue;
+ }
+ return HMX_ERROR;
+ }
+ break;
+ }
+
+ return HMX_OK;
+}
+
+/*
+ HMX_TASK_Destroy
+ ŽºÅ©¸¦ ¼Ò¸êÇÑ´Ù.
+*/
+int HMX_TASK_Destroy(unsigned long taskId)
+{
+ int rc;
+ struct HMX_TASK *task = (struct HMX_TASK *)taskId;
+
+ if( taskId == (unsigned long)NULL )
+ {
+ PrintDebug("%s(%d) taskId == NULL\n", __FUNCTION__, __LINE__);
+ return HMX_ERROR;
+ }
+ else
+ {
+ pthread_mutex_lock(&task->targ_.lock_);
+ if (task->targ_.start == 1)
+ {
+ task->targ_.start = 0;
+ }
+ rc = pthread_cancel(task->task_);
+ if (rc)
+ {
+ PrintError("[HMX_TASK_Destroy] warning : there is no thread in pthread taskId(%08X) pthreadId(%08X)\n", taskId, task->task_);
+ }
+ HMX_Sleep(1);
+#if defined(CONFIG_THREAD_JOIN_TEMPORARY)
+#else
+ if (task->targ_.IsJoinable)
+#endif
+ pthread_join(task->task_, NULL);
+
+ free(task->targ_.pucTaskStack);
+ pthread_mutex_unlock(&task->targ_.lock_);
+ }
+
+ free(task);
+
+ return HMX_OK;
+}
+
+/*
+ HMX_TASK_SetCurrentPriority
+ »õ·Î¿î ¿ì¼±¼øÀ§¸¦ ¼¼ÆÃÇÑ´Ù.
+*/
+int HMX_TASK_SetCurrentPriority(unsigned long taskId, unsigned long newpriority)
+{
+ int rc;
+ int policy;
+ struct HMX_TASK *task = (struct HMX_TASK *)taskId;
+ struct sched_param schParam;
+
+ if (task == NULL)
+ {
+ return HMX_ERROR;
+ }
+
+ rc = pthread_getschedparam(task->task_, &policy, &schParam);
+ if (schParam.sched_priority == (int)newpriority)
+ {
+ return HMX_OK;
+ }
+
+ schParam.sched_priority = newpriority;
+
+ pthread_mutex_lock(&task->targ_.lock_);
+ rc = pthread_setschedparam(task->task_, policy, &schParam);
+ pthread_mutex_unlock(&task->targ_.lock_);
+
+ if (rc) {
+ return HMX_ERROR;
+ }
+
+ return HMX_OK;
+}
+
+
+
+/*
+ list_init
+ HMX_MSG_queue ±¸Á¶Ã¼¸¦ ÃʱâÈ ÇÑ´Ù.
+*/
+void list_init(struct HMX_MSG_queue *list, unsigned long ulSize, unsigned long ulCount, unsigned char ucSuspendType)
+{
+ int i;
+
+ list->curr_msg_count_ = 0;
+ list->msg_size_ = ulSize;
+ list->msg_count_ = ulCount;
+ list->writer_count_ = 0;
+ list->reader_count_ = 0;
+ list->suspend_type_ = ucSuspendType;
+ pthread_mutex_init(&list->q_lock_, NULL);
+ pthread_cond_init(&list->q_not_empty_, NULL);
+ pthread_cond_init(&list->q_not_full_, NULL);
+
+ list->temp_head = NULL;
+ list->temp_tail = NULL;
+
+ for(i=0; i<MSG_PRIORITY_MAX; i++)
+ {
+ list->head[i] = NULL;
+ list->tail[i] = NULL;
+ list->bitmap_count[i] = 0;
+ list->bitmap[i] = 0;
+ }
+
+#ifdef HMX_MSG_DEBUG
+ list->sendTick = 0;
+ list->receiveTick = 0;
+ list->lastSendTick = 0;
+ list->lastReceiveTick = 0;
+#endif
+ return;
+}
+
+
+
+/*
+ list_destroy
+ HMX_MSG_queue ±¸Á¶Ã¼¸¦ ¼Ò¸ê½ÃŲ´Ù.
+*/
+void list_destroy(struct HMX_MSG_queue *list)
+{
+ void *data;
+
+ data = (char *)malloc(list->msg_size_);
+
+ while (list_size(list) > 0)
+ {
+ if ( list_rem_next(list, (void *)data, list->msg_size_, FALSE, FALSE) != 0 )
+ {
+ PrintError("%s : list_rem_next Error!!\n", __func__);
+ }
+ }
+
+ free(data);
+ return;
+}
+
+
+
+/*
+ list_ins_next
+ element¿¡ data¸¦ Ãß°¡ÇÑ´Ù.
+*/
+int list_ins_next(struct HMX_MSG_queue *list, unsigned long prio, const void *data, unsigned long size, unsigned char timeoutflag, struct timespec *timeo)
+{
+ struct HMX_MSG_element *new_element;
+ int rc = 0;
+
+ PrintEnter();
+
+ list->writer_count_++;
+
+ while (list->msg_count_ == list->curr_msg_count_ && 0 == rc)
+ {
+ if(TRUE == timeoutflag)
+ {
+ rc = pthread_cond_timedwait(&list->q_not_full_, &list->q_lock_, timeo);
+ }
+ else
+ {
+ rc = pthread_cond_wait(&list->q_not_full_, &list->q_lock_);
+ }
+ }
+
+ list->writer_count_--;
+
+ if(rc != 0)
+ {
+ PrintDebug("%s : rc[%d] !!\n", __FUNCTION__, rc);
+ return rc;
+ }
+
+ q_remove_temp_tail_element(list, &new_element);
+
+ memcpy(new_element->data, data, size);
+
+ if(list->tail[prio] == NULL)
+ {
+ list->head[prio] = new_element;
+ new_element->next = NULL;
+ new_element->prev = NULL;
+ list->tail[prio] = new_element;
+ }
+ else
+ {
+ list->tail[prio]->next = new_element;
+ new_element->next = NULL;
+ new_element->prev = list->tail[prio];
+ list->tail[prio] = new_element;
+ }
+
+ list->curr_msg_count_++;
+ list_bitmap_count_increase(list, prio);
+ list_set_bitmap(list, prio);
+
+ if (list->reader_count_ > 0)
+ pthread_cond_signal(&list->q_not_empty_);
+
+ PrintExit();
+ return HMX_OK;
+}
+
+
+
+
+/*
+ HMX_MSG_Init
+ ¸Þ¼¼Áö Å¥¸¦ ÃʱâÈ ÇÑ´Ù.
+*/
+int HMX_MSG_Init(void)
+{
+#if defined(HMX_MSG_DEBUG)
+ TAILQ_INIT(&msg_q_list_head);
+#endif
+ return HMX_OK;
+}
+
+
+/*
+ HMX_MSG_Create
+ ¸Þ¼¼Áö Å¥¸¦ »ý¼ºÇÑ´Ù.
+*/
+int HMX_MSG_Create(unsigned long q_count, unsigned long msg_size,
+ const char *q_name, unsigned long *q_id, HMX_SUSPENDTYPE suspendType)
+{
+ struct HMX_MSG_queue *q;
+ struct HMX_MSG_element *q_element;
+ unsigned long i;
+ struct HMX_MSG_element *q_element_pool;
+ unsigned char *data_pool;
+ HAPPY(q_name);
+
+ PrintEnter();
+
+ if(suspendType >= HMX_SUSPENDTYPE_MAX)
+ {
+ PrintError("%s[%d] : ulSuspendType %d Error\n", __FUNCTION__, __LINE__, suspendType);
+ return HMX_ERROR;
+ }
+
+ if((q = (struct HMX_MSG_queue *)malloc(sizeof(struct HMX_MSG_queue))) == NULL)
+ {
+ PrintError("%s[%d] : malloc Error\n", __FUNCTION__, __LINE__);
+ return HMX_ERROR;
+ }
+
+ memset(q, 0, sizeof(struct HMX_MSG_queue));
+
+ list_init(q, msg_size, q_count, suspendType);
+ q_element_pool = (struct HMX_MSG_element *)malloc(sizeof(struct HMX_MSG_element)*q_count);
+ data_pool = (unsigned char *)malloc(msg_size*q_count);
+ for(i=0; i<q_count; i++)
+ {
+ q_element = &q_element_pool[i];
+ q_element->data = &data_pool[i*msg_size];
+ q_insert_temp_tail_element(q, q_element);
+ }
+ q->pDataPool = data_pool;
+ q->pPool = q_element_pool;
+
+ *q_id = (unsigned long)q;
+
+#if defined(HMX_MSG_DEBUG)
+ TAILQ_INSERT_TAIL(&msg_q_list_head, q, entries);
+#endif
+#if defined(CONFIG_DEBUG)
+ if (q_name)
+ strncpy(q->name, q_name, sizeof(q->name)-1);
+ else
+ q->name[0] = 0;
+#endif
+ PrintExit();
+
+ return HMX_OK;
+}
+
+
+/*
+ HMX_MSG_Destroy
+ ¸Þ¼¼ÁöÅ¥¸¦ ¼Ò¸ê½ÃŲ´Ù.
+*/
+int HMX_MSG_Destroy(unsigned long q_id)
+{
+ struct HMX_MSG_queue *q;
+
+ PrintEnter();
+
+ q = (struct HMX_MSG_queue *)q_id;
+
+ if(q == NULL)
+ {
+ return HMX_ERROR;
+ }
+
+ pthread_cond_destroy(&q->q_not_full_);
+ pthread_cond_destroy(&q->q_not_empty_);
+ pthread_mutex_destroy(&q->q_lock_);
+
+ list_destroy(q);
+ q_destory_temp_tail(q);
+
+#if defined(HMX_MSG_DEBUG)
+ TAILQ_REMOVE(&msg_q_list_head, q, entries);
+#endif
+
+ if(q != NULL)
+ {
+ free(q);
+ }
+
+ PrintExit();
+
+ return HMX_OK;
+}
+
+int HMX_MSG_Clear(unsigned long q_id)
+{
+ struct HMX_MSG_queue *q;
+ int rc = HMX_OK;
+ // struct timespec cur_time;
+ long long exp_nsec;
+ struct timespec timeo, cur_time;
+ unsigned long size;
+ void *pBuf;
+
+
+ PrintEnter();
+
+ q = (struct HMX_MSG_queue *)q_id;
+
+ size = q->msg_size_;
+ pBuf = malloc(size);
+ if (pBuf == NULL)
+ return HMX_ERROR;
+
+ (void)pthread_mutex_lock(&q->q_lock_);
+ do
+ {
+
+ clock_gettime(CLOCK_REALTIME, &cur_time);
+ exp_nsec = (long long)cur_time.tv_sec * (long long)1000 * (long long)1000 * (long long)1000 + (long long)cur_time.tv_nsec;
+ timeo.tv_sec = exp_nsec / (1000 * 1000 * 1000);
+ timeo.tv_nsec = exp_nsec % (1000 * 1000 * 1000);
+
+ rc = list_rem_next(q, pBuf, size, TRUE, &timeo);
+ if(HMX_OK != rc)
+ {
+ if(ETIMEDOUT == rc)
+ {
+ (void)pthread_mutex_unlock(&q->q_lock_);
+ free(pBuf);
+ return HMX_OK;
+ }
+ }
+ }while (1);
+#ifdef DEBUG_MSG_LIST_PRINT
+ print_list(q);
+#endif
+
+ (void)pthread_mutex_unlock(&q->q_lock_);
+
+ free(pBuf);
+ PrintExit();
+ return HMX_OK;
+}
+
+
+/*
+ HMX_MSG_Send
+ ¸Þ¼¼Áö¸¦ º¸³½´Ù.
+*/
+int HMX_MSG_Send(unsigned long q_id, const void *msg, unsigned long size)
+{
+ struct HMX_MSG_queue *q;
+ int rc = HMX_OK;
+ unsigned long prio;
+
+ PrintEnter();
+
+ q = (struct HMX_MSG_queue *)q_id;
+
+ if(size > q->msg_size_)
+ {
+ PrintError("%s[%d] : size %ld Error\n", __FUNCTION__, __LINE__, size);
+ return HMX_ERROR;
+ }
+
+ HMX_TASK_CheckCallback();
+
+ rc = P_MSG_Check(q, q_id);
+ if (HMX_OK != rc)
+ {
+#if defined(CONFIG_DEBUG)
+ PrintError("%s(%d) : P_MSG_Check : HMX_MSG_FULL!! queue name (%s)\n", __func__, __LINE__, q->name);
+#endif
+ return rc;
+ }
+
+ if(HMX_SUSPENDTYPE_PRIORITY == q->suspend_type_)
+ {
+ rc = list_find_msg_q_priority_from_task_priority(&prio);
+ if(rc != HMX_OK)
+ {
+ prio = MSG_PRIORITY0;
+ }
+ }
+ else
+ {
+ prio = MSG_PRIORITY0;
+ }
+
+ (void)pthread_mutex_lock(&q->q_lock_);
+
+ rc = list_ins_next(q, prio, msg, size, FALSE, NULL);
+
+ if(HMX_OK != rc)
+ {
+ PrintError("%s : list_ins_next() rc[%d] Error!!\n", __FUNCTION__, rc);
+ (void)pthread_mutex_unlock(&q->q_lock_);
+ return rc;
+ }
+
+#ifdef DEBUG_MSG_LIST_PRINT
+ print_list(q);
+#endif
+
+ (void)pthread_mutex_unlock(&q->q_lock_);
+
+#ifdef HMX_MSG_DEBUG
+ q->lastSendTick = VK_TIMER_GetSystemTick();
+#endif
+
+ PrintExit();
+
+ return HMX_OK;
+}
+
+
+
+/*
+ HMX_MSG_SendTimeout
+ ¸Þ¼¼Áö¸¦ Timeout³»¿¡ º¸³½´Ù.
+*/
+int HMX_MSG_SendTimeout(unsigned long q_id, const void *msg, unsigned long size, unsigned long timeout)
+{
+ struct HMX_MSG_queue *q;
+ int rc = HMX_OK;
+ unsigned long prio = 0;
+ struct timespec timeo;
+ struct timespec cur_time;
+ long long exp_nsec;
+
+ PrintEnter();
+
+ if (timeout != 0)
+ {
+// HMX_TASK_CheckCallback();
+ }
+ if (timeout == 0xFFFFFFFF)
+ {
+ return HMX_MSG_Send(q_id, msg, size);
+ }
+
+ q = (struct HMX_MSG_queue *)q_id;
+
+ if(size > q->msg_size_)
+ {
+ PrintError("%s[%d] : size %ld Error\n", __FUNCTION__, __LINE__, size);
+ return HMX_ERROR;
+ }
+
+ rc = P_MSG_Check(q, q_id);
+ if (HMX_OK != rc)
+ {
+#if defined(CONFIG_DEBUG)
+ PrintError("%s(%d) : P_MSG_Check : HMX_MSG_FULL!! queue name : %s\n", __func__, __LINE__, q->name);
+#endif
+ return rc;
+ }
+
+ if(HMX_SUSPENDTYPE_PRIORITY == q->suspend_type_)
+ {
+ rc = list_find_msg_q_priority_from_task_priority(&prio);
+ if(rc != HMX_OK)
+ {
+ prio = MSG_PRIORITY0;
+ }
+ }
+ else
+ {
+ prio = MSG_PRIORITY0;
+ }
+
+ clock_gettime(CLOCK_REALTIME, &cur_time);
+ exp_nsec = (long long)cur_time.tv_sec * 1000 * 1000 * 1000 + cur_time.tv_nsec;
+ if (timeout != 0)
+ exp_nsec += (timeout * 1000 - 999) * 1000;
+ timeo.tv_sec = exp_nsec / (1000 * 1000 * 1000);
+ timeo.tv_nsec = exp_nsec % (1000 * 1000 * 1000);
+
+ (void)pthread_mutex_lock(&q->q_lock_);
+
+ rc = list_ins_next(q, prio, msg, size, TRUE, &timeo);
+ if(HMX_OK != rc)
+ {
+ (void)pthread_mutex_unlock(&q->q_lock_);
+
+ if(ETIMEDOUT == rc)
+ {
+ PrintDebug("%s : list_ins_next() rc[%d] HMX_TIMEOUT!!\n", __FUNCTION__, rc);
+ return HMX_TIMEOUT;
+ }
+ else
+ {
+ PrintError("%s : list_ins_next() rc[%d] Error!!\n", __FUNCTION__, rc);
+ return HMX_ERROR;
+ }
+ }
+
+#ifdef DEBUG_MSG_LIST_PRINT
+ print_list(q);
+#endif
+
+ (void)pthread_mutex_unlock(&q->q_lock_);
+
+ PrintExit();
+
+ return HMX_OK;
+}
+
+
+/*
+ HMX_MSG_SendUrgent
+ ±ä±Þ ¸Þ¼¼Áö¸¦ º¸³½´Ù.
+*/
+int HMX_MSG_SendUrgent(unsigned long q_id, const void *msg, unsigned long size)
+{
+ struct HMX_MSG_queue *q;
+ int rc = HMX_OK;
+ unsigned long prio;
+
+ PrintEnter();
+
+ q = (struct HMX_MSG_queue *)q_id;
+
+ if(size > q->msg_size_)
+ {
+ PrintError("%s[%d] : size %ld Error\n", __FUNCTION__, __LINE__, size);
+ return HMX_ERROR;
+ }
+
+ rc = P_MSG_Check(q, q_id);
+ if (HMX_OK != rc)
+ {
+#if defined(CONFIG_DEBUG)
+ PrintError("%s(%d) : P_MSG_Check : HMX_MSG_FULL!! queue name (%s)\n", __func__, __LINE__, q->name);
+#endif
+ return rc;
+ }
+
+ if(HMX_SUSPENDTYPE_PRIORITY == q->suspend_type_)
+ {
+ prio = MSG_PRIORITY_MAX-1; //°¡Àå ³ôÀº ¿ì¼±¼øÀ§·Î º¸³½´Ù.
+ }
+ else
+ {
+ prio = MSG_PRIORITY0;
+ }
+
+ (void)pthread_mutex_lock(&q->q_lock_);
+
+ rc = list_ins_next(q, prio, msg, size, FALSE, FALSE);
+ if(HMX_OK != rc)
+ {
+ PrintError("%s : list_ins_next() rc[%d] Error!!\n", __FUNCTION__, rc);
+ (void)pthread_mutex_unlock(&q->q_lock_);
+ return rc;
+ }
+
+#ifdef DEBUG_MSG_LIST_PRINT
+ print_list(q);
+#endif
+
+ (void)pthread_mutex_unlock(&q->q_lock_);
+
+#ifdef HMX_MSG_DEBUG
+ q->lastSendTick = VK_TIMER_GetSystemTick();
+#endif
+
+ PrintExit();
+
+ return HMX_OK;
+}
+
+
+/*
+ HMX_MSG_SendUrgentTimeout
+ ±ä±Þ ¸Þ¼¼Áö¸¦ Timeout ³»¿¡ º¸³½´Ù.
+*/
+int HMX_MSG_SendUrgentTimeout(unsigned long q_id, const void *msg, unsigned long size, unsigned long timeout)
+{
+ struct HMX_MSG_queue *q;
+ int rc = HMX_OK;
+ unsigned long prio = 0;
+ struct timespec timeo;
+ struct timespec cur_time;
+ long long exp_nsec;
+
+ PrintEnter();
+
+ if (timeout == 0xFFFFFFFF)
+ {
+ return HMX_MSG_SendUrgent(q_id, msg, size);
+ }
+
+ q = (struct HMX_MSG_queue *)q_id;
+
+ if(size > q->msg_size_)
+ {
+ PrintError("%s[%d] : size %ld Error\n", __FUNCTION__, __LINE__, size);
+ return HMX_ERROR;
+ }
+
+ rc = P_MSG_Check(q, q_id);
+ if (HMX_OK != rc)
+ {
+#if defined(CONFIG_DEBUG)
+ PrintError("%s(%d) : P_MSG_Check : HMX_MSG_FULL!! queue name(%s)\n", __func__, __LINE__, q->name);
+#endif
+ return rc;
+ }
+
+ if(HMX_SUSPENDTYPE_PRIORITY == q->suspend_type_)
+ {
+ prio = MSG_PRIORITY_MAX-1; //°¡Àå ³ôÀº ¿ì¼±¼øÀ§·Î º¸³½´Ù.
+ }
+ else
+ {
+ prio = MSG_PRIORITY0;
+ }
+
+ clock_gettime(CLOCK_REALTIME, &cur_time);
+ exp_nsec = (long long)cur_time.tv_sec * 1000 * 1000 * 1000 + cur_time.tv_nsec;
+ if (timeout != 0)
+ exp_nsec += (timeout * 1000 - 999) * 1000;
+ timeo.tv_sec = exp_nsec / (1000 * 1000 * 1000);
+ timeo.tv_nsec = exp_nsec % (1000 * 1000 * 1000);
+
+ (void)pthread_mutex_lock(&q->q_lock_);
+
+ rc = list_ins_next(q, prio, msg, size, TRUE, &timeo);
+
+ if(HMX_OK != rc)
+ {
+ (void)pthread_mutex_unlock(&q->q_lock_);
+
+ if(ETIMEDOUT == rc)
+ {
+ PrintDebug("%s : list_ins_next() rc[%d] HMX_TIMEOUT!!\n", __FUNCTION__, rc);
+ return HMX_TIMEOUT;
+ }
+ else
+ {
+ PrintError("%s : list_ins_next() rc[%d] Error!!\n", __FUNCTION__, rc);
+ return HMX_ERROR;
+ }
+ }
+
+#ifdef DEBUG_MSG_LIST_PRINT
+ print_list(q);
+#endif
+
+ (void)pthread_mutex_unlock(&q->q_lock_);
+
+ PrintExit();
+
+ return HMX_OK;
+}
+
+#if defined(HMX_MSG_DEBUG) && defined(VK_TASK_DEBUG)
+#define HMX_MSG_CRITICAL_DELAY_TICK 20
+#define HMX_MSG_NORMAL_DELAY_TICK 200
+#endif
+/*
+ HMX_MSG_Receive
+ ¸Þ¼¼Áö¸¦ ¹Þ´Â´Ù.
+*/
+int HMX_MSG_Receive(unsigned long q_id, void *msg, unsigned long size)
+{
+ struct HMX_MSG_queue *q;
+// unsigned long prio;
+ int rc = HMX_OK;
+
+ PrintEnter();
+
+ HMX_TASK_CheckCallback();
+
+ q = (struct HMX_MSG_queue *)q_id;
+
+ if(size > q->msg_size_)
+ {
+ PrintError("%s : size %ld Error!!\n", __FUNCTION__, size);
+ return HMX_ERROR;
+ }
+
+ (void)pthread_mutex_lock(&q->q_lock_);
+
+#if defined(HMX_MSG_DEBUG) && defined(VK_TASK_DEBUG)
+ q->receiveTick = VK_TIMER_GetSystemTick();
+ if (q->lastReceiveTick != 0 && (q->receiveTick - q->lastReceiveTick > HMX_MSG_NORMAL_DELAY_TICK))
+ {
+ if ((q->receiveTick - tickForVkDebug) > HMX_MSG_CRITICAL_DELAY_TICK)
+ {
+ PrintError("HMX_MSG_Receive : It has excuted too long time (%d) queue(%s)\n", q->receiveTick - q->lastReceiveTick, q->name);
+ }
+ }
+#endif
+ rc = list_rem_next(q, msg, size, FALSE, NULL);
+#if defined(HMX_MSG_DEBUG) && defined(VK_TASK_DEBUG)
+ q->lastReceiveTick = tickForVkDebug = VK_TIMER_GetSystemTick();
+#endif
+ if(HMX_OK != rc)
+ {
+ PrintError("%s : list_rem_next() rc[%d] Error!!\n", __FUNCTION__, rc);
+ (void)pthread_mutex_unlock(&q->q_lock_);
+ return rc;
+ }
+
+#ifdef DEBUG_MSG_LIST_PRINT
+ print_list(q);
+#endif
+ (void)pthread_mutex_unlock(&q->q_lock_);
+
+ PrintExit();
+ return HMX_OK;
+}
+
+/*
+ HMX_MSG_ReceiveTimeout
+ ¸Þ¼¼Áö¸¦ Timeout³»¿¡ ¹Þ´Â´Ù.
+*/
+int HMX_MSG_ReceiveTimeout(unsigned long q_id, void *msg, unsigned long size, unsigned long timeout)
+{
+ struct HMX_MSG_queue *q;
+ int rc = HMX_OK;
+ // struct timespec cur_time;
+ long long exp_nsec;
+ struct timespec timeo, cur_time;
+
+ PrintEnter();
+ if (timeout != 0)
+ {
+ HMX_TASK_CheckCallback();
+ }
+
+ if (timeout == 0xFFFFFFFF)
+ {
+ return HMX_MSG_Receive(q_id, msg, size);
+ }
+
+ q = (struct HMX_MSG_queue *)q_id;
+
+ if(size > q->msg_size_)
+ {
+ PrintError("%s : size %ld Error!!\n", __FUNCTION__, size);
+ return HMX_ERROR;
+ }
+
+ clock_gettime(CLOCK_REALTIME, &cur_time);
+ exp_nsec = (long long)cur_time.tv_sec * (long long)1000 * (long long)1000 * (long long)1000 + (long long)cur_time.tv_nsec;
+ if (timeout != 0)
+ exp_nsec += (long long)(timeout * (long long)1000 - 999) * (long long)1000;
+ timeo.tv_sec = exp_nsec / (1000 * 1000 * 1000);
+ timeo.tv_nsec = exp_nsec % (1000 * 1000 * 1000);
+
+ (void)pthread_mutex_lock(&q->q_lock_);
+#if defined(HMX_MSG_DEBUG) && defined(VK_TASK_DEBUG)
+ q->receiveTick = VK_TIMER_GetSystemTick();
+ if (q->lastReceiveTick != 0 && (q->receiveTick - q->lastReceiveTick > HMX_MSG_NORMAL_DELAY_TICK))
+ {
+ if ((q->receiveTick - tickForVkDebug) > HMX_MSG_CRITICAL_DELAY_TICK)
+ {
+ PrintError("HMX_MSG_ReceiveTimeout : It has excuted too long time (%d) queue(%s)\n", q->receiveTick - q->lastReceiveTick, q->name);
+ }
+ }
+#endif
+
+ rc = list_rem_next(q, msg, size, TRUE, &timeo);
+#if defined(HMX_MSG_DEBUG) && defined(VK_TASK_DEBUG)
+ q->lastReceiveTick = tickForVkDebug = VK_TIMER_GetSystemTick();
+#endif
+ if(HMX_OK != rc)
+ {
+ (void)pthread_mutex_unlock(&q->q_lock_);
+
+ if(ETIMEDOUT == rc)
+ {
+ PrintDebug("%s : list_rem_next() rc[%d] HMX_TIMEOUT!!\n", __FUNCTION__, rc);
+ return HMX_TIMEOUT;
+ }
+ else
+ {
+ PrintError("%s : list_rem_next() rc[%d] Error!!\n", __FUNCTION__, rc);
+ return HMX_ERROR;
+ }
+ }
+
+#ifdef DEBUG_MSG_LIST_PRINT
+ print_list(q);
+#endif
+
+ (void)pthread_mutex_unlock(&q->q_lock_);
+
+ PrintExit();
+ return HMX_OK;
+}
+
+int HMX_MSG_GetMessageCount(unsigned long q_id, unsigned long *pulMsgCount, unsigned long *pulMaxMsgCount)
+{
+ struct HMX_MSG_queue *q;
+
+ PrintEnter();
+
+ q = (struct HMX_MSG_queue *)q_id;
+
+ (void)pthread_mutex_lock(&q->q_lock_);
+ *pulMsgCount = q->curr_msg_count_;
+ *pulMaxMsgCount = q->msg_count_;
+ (void)pthread_mutex_unlock(&q->q_lock_);
+
+ PrintExit();
+ return HMX_OK;
+}
+
+static int P_MSG_Check(struct HMX_MSG_queue *q, unsigned long q_id)
+{
+ unsigned long ulNearlyFullCount;
+#if !defined(CONFIG_DEBUG)
+ UNUSED(q_id);
+#endif
+
+ ulNearlyFullCount = (q->msg_count_ * 3);
+ ulNearlyFullCount = ulNearlyFullCount/4;
+
+ if(q->msg_count_ == q->curr_msg_count_)
+ {
+#if defined(CONFIG_DEBUG)
+ if (VK_TIMER_GetSystemTick() - tickForVkDebug > 5000)
+ {
+ tickForVkDebug = VK_TIMER_GetSystemTick();
+ // queue is full.
+#if defined(CONFIG_DEBUG)
+ PrintError("\n!!\n!!! %s(): WARNING: queue_id 0x%X, name:%s full !!!%c\n!!!\n", __FUNCTION__, q_id, q->name, 7);
+ #if defined(VK_TASK_DEBUG)
+ VK_TASK_PrintTaskList();
+ #endif
+ #if defined(HMX_MSG_DEBUG)
+ HMX_MSG_PrintMsgQList();
+ #endif
+ #if defined(VK_SEM_DEBUG)
+ VK_SEM_PrintSemList();
+ #endif
+#else
+ PrintError("\n!!\n!!! %s(): WARNING: queue_id 0x%X, full !!!%c\n!!!\n", __FUNCTION__, q_id, 7);
+#endif
+ }
+#endif
+ return HMX_MSG_FULL;
+ }
+ else if( q->curr_msg_count_ > ulNearlyFullCount )
+ {
+#if defined(CONFIG_DEBUG)
+ PrintError("[HMX_MSG_Send] MsgQue is nearly full - SendTask:%d, QueId:0x%X, (%ld, %ld), name:%s\r\n",
+ pthread_self(), q_id, q->msg_count_, q->curr_msg_count_, q->name);
+#endif
+ }
+
+ return HMX_OK;
+}
+
+
+/*
+ HMX_MSG_PrintMsgQList
+ ¸Þ¼¼ÁöÅ¥ Á¤º¸¸¦ Ãâ·ÂÇÑ´Ù.
+*/
+#if defined(HMX_MSG_DEBUG)
+void HMX_MSG_PrintMsgQList(void)
+{
+ HINT32 ulCnt=0;
+ struct HMX_MSG_queue *pMsgQ;
+
+ PrintDebug("**********************************************************\n");
+ PrintDebug(" Name Qid Size Count Cur_Count Type\n");
+ for (pMsgQ = msg_q_list_head.tqh_first; pMsgQ != NULL; pMsgQ = pMsgQ->entries.tqe_next)
+ {
+ PrintDebug("[%03d]%20s 0x%08X %04d %05d %09d %04d\n",ulCnt,
+ pMsgQ->name, (unsigned long)pMsgQ, pMsgQ->msg_size_, pMsgQ->msg_count_, pMsgQ->curr_msg_count_, pMsgQ->suspend_type_);
+ ulCnt++;
+ }
+ PrintDebug("**********************************************************\n");
+}
+#endif
+
+
+/*@}*/
diff --git a/libupgrade/hmx_upgrade_system.h b/libupgrade/hmx_upgrade_system.h
new file mode 100644
index 0000000..2d51d21
--- /dev/null
+++ b/libupgrade/hmx_upgrade_system.h
@@ -0,0 +1,253 @@
+/*******************************************************************/
+/************************* File Description ************************/
+/*******************************************************************/
+/* File Name: $Workfile: hmx_uprade_system.h $
+ * Version: $Revision: 1.0 $
+ * Original Author: Yang Hyun Uk $
+ * Current Author: $Author: huyang@humaxdigital.com $
+ * Date: $Date: 2011.09.30
+ * File Description: Upgrade APIs
+ * Module:
+ * Remarks:
+ */
+
+
+/**
+ * @author Hyunuk Yang(huyang@humaxdigital.com)
+ * @date 30 Sept 2011
+ */
+
+/**
+ * @note
+ * Copyright (C) 2011 Humax Corporation. All Rights Reserved. <br>
+ * This software is the confidential and proprietary information
+ * of Humax Corporation. You may not use or distribute this software
+ * except in compliance with the terms and conditions of any applicable license
+ * agreement in writing between Humax Corporation and you.
+ */
+
+ /*@{*/
+
+/**
+ * @file hmx_upgrade_system.h
+ */
+
+/*******************************************************************/
+/**************************** Header Files**************************/
+/*******************************************************************/
+/* Start Including Header Files */
+#include <stdio.h>
+#include <string.h>
+#include <stdlib.h>
+#include <pthread.h>
+#include <errno.h>
+#include <assert.h>
+#include <sys/queue.h>
+#include <unistd.h>
+#include <fcntl.h>
+/* End Including Headers*/
+
+/*******************************************************************/
+/************************ Extern variables *************************/
+/*******************************************************************/
+/* Start Extern variablee */
+
+/* End Extern variable */
+
+
+/*******************************************************************/
+/************************ Macro Definition *************************/
+/*******************************************************************/
+/* Start Macro definition */
+#define HMX_TASK_CheckCallback()
+#define HMX_OK 0
+#define HMX_ERROR 1
+#define HMX_TIMEOUT 2
+#define HMX_INVALID_ID 3
+#define HMX_ALLOC_ERROR 4
+#define HMX_NO_MSG 5
+#define HMX_CREATE_ERROR 10
+#define HMX_DESTROY_ERROR 11
+#define HMX_LOCK_ERROR 12
+#define HMX_UNLOCK_ERROR 13
+#define HMX_TIME_INFINITE 14
+#define HMX_INVALID_CLOCK 15
+#define HMX_MSG_FULL 17
+
+#define TRUE 1
+#define FALSE 0
+
+
+#define HMX_TASK_PTHREAD_STACK_MIN (16*1024)
+#define HMX_TASK_PTHREAD_DEFAULT_PRIO SCHED_RR
+
+#define HMX_TASK_STACK_OVERHEAD_SIZE 0x2000
+#define HMX_TASK_GUARD_SIZE 16
+
+/* End Macro definition */
+
+/*******************************************************************/
+/****************************** typedef ****************************/
+/*******************************************************************/
+/* Start typedef */
+
+////////////////////////////////////////////////////////////////////
+// Task Priority Set
+////////////////////////////////////////////////////////////////////
+/*
+ ÁÖÀÇ»çÇ×
+ Priority¸¦ Áõ°¡ ½ÃŲ´Ù¸é VK_MSG_PRIORITYÀÇ °ªµµ °°ÀÌ Áõ°¡ ½ÃÄÑ¾ß ÇÑ´Ù.
+ VK_MSG_PRIORITYÀÇ °ªÀº Ç×»ó priorityÀÇ °ª º¸´Ù 1 ¸¹¾Æ¾ß ±×·¡¾ß Urgent msg¸¦ ó¸® ÇÑ´Ù.
+*/
+/* Basic Priority Set */
+#define BASE_PRIORITY 60
+#define HIGHEST_PRIORITY 108
+
+#define PRIORITY_INCREMENT 1
+
+//temp :: Never use
+#define USER_PRIORITY0 BASE_PRIORITY // 60
+#define USER_PRIORITY1 (BASE_PRIORITY + PRIORITY_INCREMENT*1)
+#define USER_PRIORITY2 (BASE_PRIORITY + PRIORITY_INCREMENT*2)
+#define USER_PRIORITY3 (BASE_PRIORITY + PRIORITY_INCREMENT*3)
+#define USER_PRIORITY4 (BASE_PRIORITY + PRIORITY_INCREMENT*4)
+
+//ÀÏ´Ü default priority·Î 6¹ø »ç¿ë 50À» ±âÁØÀ¸·Î 8ÀÌ Àû´çÇÒ µí.
+#define USER_PRIORITY5 (BASE_PRIORITY + PRIORITY_INCREMENT*5)
+#define USER_PRIORITY6 (BASE_PRIORITY + PRIORITY_INCREMENT*6)
+#define USER_PRIORITY7 (BASE_PRIORITY + PRIORITY_INCREMENT*7)
+#define USER_PRIORITY8 (BASE_PRIORITY + PRIORITY_INCREMENT*8)
+#define USER_PRIORITY9 (BASE_PRIORITY + PRIORITY_INCREMENT*9)
+
+#define USER_PRIORITY10 (BASE_PRIORITY + PRIORITY_INCREMENT*10) // 80
+#define USER_PRIORITY11 (BASE_PRIORITY + PRIORITY_INCREMENT*11)
+#define USER_PRIORITY12 (BASE_PRIORITY + PRIORITY_INCREMENT*12)
+
+//temp :: for the highest DD
+#define USER_PRIORITY13 (BASE_PRIORITY + PRIORITY_INCREMENT*13)
+#define USER_PRIORITY14 (BASE_PRIORITY + PRIORITY_INCREMENT*14)
+
+//USER_PRIORITY15´Â »ç¿ëÇÏÁö ¸» °Í..... //20071011 TestByPooh
+//Only task priority adjust
+#define USER_PRIORITY15 HIGHEST_PRIORITY
+
+
+
+//MSG_PRIORITYÀÇ °ªÀº Task PriorityÀÇ °¹¼öº¸´Ù 1°³ ¸¹¾Æ¾ß ÇÑ´Ù.
+typedef enum
+{
+ MSG_PRIORITY0,
+ MSG_PRIORITY1,
+ MSG_PRIORITY2,
+ MSG_PRIORITY3,
+ MSG_PRIORITY4,
+ MSG_PRIORITY5,
+ MSG_PRIORITY6,
+ MSG_PRIORITY7,
+ MSG_PRIORITY8,
+ MSG_PRIORITY9,
+ MSG_PRIORITY10,
+ MSG_PRIORITY11,
+ MSG_PRIORITY12,
+ MSG_PRIORITY13,
+ MSG_PRIORITY14,
+ MSG_PRIORITY15,
+ MSG_PRIORITY16,
+ MSG_PRIORITY_MAX //ÃÖ»óÀ§ÀÇ PRIORITY´Â Urgent·Î »ç¿ëÇÔ..
+}HMX_MSG_PRIORITY;
+
+typedef enum
+{
+ HMX_SUSPENDTYPE_FIFO,
+ HMX_SUSPENDTYPE_PRIORITY,
+ HMX_SUSPENDTYPE_MAX
+}HMX_SUSPENDTYPE;
+
+
+/* End typedef */
+
+
+/*******************************************************************/
+/******************** global function prototype ********************/
+/*******************************************************************/
+/* Start global function prototypes */
+
+/* End global function prototypes */
+
+
+struct HMX_TASK_arg {
+ pthread_mutex_t lock_;
+ pthread_cond_t cond_;
+ unsigned long priority_;
+ unsigned long stackSize_;
+ int IsJoinable;
+ int start;
+ unsigned long *pucTaskStack;
+ unsigned long *pulStackStartAddress;
+ void (*start_func_)(void *);
+ void *arg_;
+#if defined(CONFIG_DEBUG)
+ pid_t pid;
+ pid_t tid;
+#endif
+
+#if defined(CONFIG_DEBUG)
+ int thread_id;
+#endif
+ char name[32];
+};
+
+struct HMX_TASK {
+ pthread_t task_;
+ struct HMX_TASK_arg targ_;
+};
+
+struct HMX_MSG_element
+{
+ void *data;
+ struct HMX_MSG_element *next;
+ struct HMX_MSG_element *prev;
+};
+
+struct HMX_MSG_queue
+{
+
+ pthread_mutex_t q_lock_;
+ pthread_cond_t q_not_empty_;
+ pthread_cond_t q_not_full_;
+ unsigned long curr_msg_count_;
+ unsigned long msg_size_;
+ unsigned long msg_count_;
+ unsigned long bitmap_count[MSG_PRIORITY_MAX];
+ unsigned char bitmap[MSG_PRIORITY_MAX];
+ unsigned char suspend_type_;
+ void *pPool;
+ void *pDataPool;
+
+ int writer_count_;
+ int reader_count_;
+
+ struct HMX_MSG_element *temp_head;
+ struct HMX_MSG_element *temp_tail;
+ struct HMX_MSG_element *head[MSG_PRIORITY_MAX];
+ struct HMX_MSG_element *tail[MSG_PRIORITY_MAX];
+
+#if defined(CONFIG_DEBUG)
+ unsigned long sendTick;
+ unsigned long receiveTick;
+ unsigned long lastSendTick;
+ unsigned long lastReceiveTick;
+ char name[32];
+ TAILQ_ENTRY(HMX_MSG_queue) entries;
+#endif
+};
+
+#if defined(VK_MSG_DEBUG)
+TAILQ_HEAD(listhead, HMX_MSG_queue) msg_q_list_head;
+#endif
+
+#if defined(CONFIG_DEBUG)
+unsigned long tickForVkDebug;
+#endif
+
+/*@}*/
diff --git a/libupgrade/lib_queue.c b/libupgrade/lib_queue.c
new file mode 100644
index 0000000..5957339
--- /dev/null
+++ b/libupgrade/lib_queue.c
@@ -0,0 +1,218 @@
+/* *********************************************************************
+ * Broadcom Common Firmware Environment (CFE)
+ *
+ * Queue Management routines File: lib_queue.c
+ *
+ * Routines to manage doubly-linked queues.
+ *
+ * Author: Mitch Lichtenberg (mpl@broadcom.com)
+ *
+ *********************************************************************
+ *
+ * Copyright 2000,2001
+ * Broadcom Corporation. All rights reserved.
+ *
+ * This software is furnished under license and may be used and
+ * copied only in accordance with the following terms and
+ * conditions. Subject to these conditions, you may download,
+ * copy, install, use, modify and distribute modified or unmodified
+ * copies of this software in source and/or binary form. No title
+ * or ownership is transferred hereby.
+ *
+ * 1) Any source code used, modified or distributed must reproduce
+ * and retain this copyright notice and list of conditions as
+ * they appear in the source file.
+ *
+ * 2) No right is granted to use any trade name, trademark, or
+ * logo of Broadcom Corporation. Neither the "Broadcom
+ * Corporation" name nor any trademark or logo of Broadcom
+ * Corporation may be used to endorse or promote products
+ * derived from this software without the prior written
+ * permission of Broadcom Corporation.
+ *
+ * 3) THIS SOFTWARE IS PROVIDED "AS-IS" AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING BUT NOT LIMITED TO, ANY IMPLIED
+ * WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+ * PURPOSE, OR NON-INFRINGEMENT ARE DISCLAIMED. IN NO EVENT
+ * SHALL BROADCOM BE LIABLE FOR ANY DAMAGES WHATSOEVER, AND IN
+ * PARTICULAR, BROADCOM SHALL NOT BE LIABLE FOR DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
+ * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
+ * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
+ * TORT (INCLUDING NEGLIGENCE OR OTHERWISE), EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ ********************************************************************* */
+
+#include "lib_queue.h"
+
+
+/* *********************************************************************
+ * Q_ENQUEUE(qb,item)
+ *
+ * Add item to a queue
+ *
+ * Input Parameters:
+ * qb - queue block
+ * item - item to add
+ *
+ * Return Value:
+ * Nothing.
+ ********************************************************************* */
+
+void q_enqueue(queue_t *qb,queue_t *item)
+{
+ qb->q_prev->q_next = item;
+ item->q_next = qb;
+ item->q_prev = qb->q_prev;
+ qb->q_prev = item;
+}
+
+
+/* *********************************************************************
+ * Q_DEQUEUE(element)
+ *
+ * Remove an element from the queue
+ *
+ * Input Parameters:
+ * element - element to remove
+ *
+ * Return Value:
+ * Nothing.
+ ********************************************************************* */
+
+void q_dequeue(queue_t *item)
+{
+ item->q_prev->q_next = item->q_next;
+ item->q_next->q_prev = item->q_prev;
+}
+
+
+/* *********************************************************************
+ * Q_DEQNEXT(qb)
+ *
+ * Dequeue next element from the specified queue
+ *
+ * Input Parameters:
+ * qb - queue block
+ *
+ * Return Value:
+ * next element, or NULL
+ ********************************************************************* */
+
+queue_t *q_deqnext(queue_t *qb)
+{
+ if (qb->q_next == qb) {
+ return NULL;
+ }
+
+ qb = qb->q_next;
+
+ qb->q_prev->q_next = qb->q_next;
+ qb->q_next->q_prev = qb->q_prev;
+
+ return qb;
+}
+
+
+/* *********************************************************************
+ * Q_MAP(qb)
+ *
+ * "Map" a queue, calling the specified function for each
+ * element in the queue
+ *
+ * If the function returns nonzero, q_map will terminate.
+ *
+ * Input Parameters:
+ * qb - queue block
+ * fn - function pointer
+ * a,b - parameters for the function
+ *
+ * Return Value:
+ * return value from function, or zero if entire queue
+ * was mapped.
+ ********************************************************************* */
+
+int q_map(queue_t *qb, int (*func)(queue_t *,unsigned int,unsigned int),
+ unsigned int a,unsigned int b)
+{
+ queue_t *qe;
+ queue_t *nextq;
+ int res;
+
+ qe = qb;
+
+ qe = qb->q_next;
+
+ while (qe != qb) {
+ nextq = qe->q_next;
+ if ((res = (*func)(qe,a,b))) return res;
+ qe = nextq;
+ }
+
+ return 0;
+}
+
+
+
+
+
+/* *********************************************************************
+ * Q_COUNT(qb) *
+ * *
+ * Counts the elements on a queue (not interlocked) *
+ * *
+ * Input Parameters: *
+ * qb - queue block *
+ * *
+ * Return Value: *
+ * number of elements *
+ ********************************************************************* */
+int q_count(queue_t *qb)
+{
+ queue_t *qe;
+ int res = 0;
+
+ qe = qb;
+
+ while (qe->q_next != qb) {
+ qe = qe->q_next;
+ res++;
+ }
+
+ return res;
+}
+
+
+
+
+/* *********************************************************************
+ * Q_FIND(qb,item)
+ *
+ * Determines if a particular element is on a queue.
+ *
+ * Input Parameters:
+ * qb - queue block
+ * item - queue element
+ *
+ * Return Value:
+ * 0 - not on queue
+ * >0 - position on queue
+ ********************************************************************* */
+int q_find(queue_t *qb,queue_t *item)
+{
+ queue_t *q;
+ int res = 1;
+
+ q = qb->q_next;
+
+ while (q != item) {
+ if (q == qb) return 0;
+ q = q->q_next;
+ res++;
+ }
+
+ return res;
+}
+
diff --git a/libupgrade/lib_queue.h b/libupgrade/lib_queue.h
new file mode 100644
index 0000000..02ab2f5
--- /dev/null
+++ b/libupgrade/lib_queue.h
@@ -0,0 +1,100 @@
+/* *********************************************************************
+ * Broadcom Common Firmware Environment (CFE)
+ *
+ * Queue management prototypes File: lib_queue.h
+ *
+ * Constants, structures, and function prototypes for the queue
+ * manager.
+ *
+ * Author: Mitch Lichtenberg (mpl@broadcom.com)
+ *
+ *********************************************************************
+ *
+ * Copyright 2000,2001
+ * Broadcom Corporation. All rights reserved.
+ *
+ * This software is furnished under license and may be used and
+ * copied only in accordance with the following terms and
+ * conditions. Subject to these conditions, you may download,
+ * copy, install, use, modify and distribute modified or unmodified
+ * copies of this software in source and/or binary form. No title
+ * or ownership is transferred hereby.
+ *
+ * 1) Any source code used, modified or distributed must reproduce
+ * and retain this copyright notice and list of conditions as
+ * they appear in the source file.
+ *
+ * 2) No right is granted to use any trade name, trademark, or
+ * logo of Broadcom Corporation. Neither the "Broadcom
+ * Corporation" name nor any trademark or logo of Broadcom
+ * Corporation may be used to endorse or promote products
+ * derived from this software without the prior written
+ * permission of Broadcom Corporation.
+ *
+ * 3) THIS SOFTWARE IS PROVIDED "AS-IS" AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING BUT NOT LIMITED TO, ANY IMPLIED
+ * WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
+ * PURPOSE, OR NON-INFRINGEMENT ARE DISCLAIMED. IN NO EVENT
+ * SHALL BROADCOM BE LIABLE FOR ANY DAMAGES WHATSOEVER, AND IN
+ * PARTICULAR, BROADCOM SHALL NOT BE LIABLE FOR DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
+ * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
+ * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
+ * TORT (INCLUDING NEGLIGENCE OR OTHERWISE), EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ ********************************************************************* */
+
+
+#ifndef _LIB_QUEUE_H
+#define _LIB_QUEUE_H
+
+/* *********************************************************************
+ * Macros
+ ********************************************************************* */
+
+#define q_init(q) (q)->q_prev = (q), (q)->q_next = (q)
+#define q_isempty(q) ((q)->q_next == (q))
+#define q_getfirst(q) ((q)->q_next)
+#define q_getlast(q) ((q)->q_prev)
+
+/* *********************************************************************
+ * Types
+ ********************************************************************* */
+
+#ifndef NULL
+#define NULL 0
+#endif
+
+#ifndef TRUE
+#define TRUE 1
+#endif
+
+#ifndef FALSE
+#define FALSE 0
+#endif
+
+
+typedef struct queue_s {
+ struct queue_s *q_next;
+ struct queue_s *q_prev;
+} queue_t;
+
+
+/* *********************************************************************
+ * Prototypes
+ ********************************************************************* */
+
+void q_enqueue(queue_t *,queue_t *);
+void q_dequeue(queue_t *);
+queue_t *q_deqnext(queue_t *);
+int q_map(queue_t *qb,int (*func)(queue_t *,unsigned int,unsigned int),
+ unsigned int a,unsigned int b);
+int q_count(queue_t *);
+int q_find(queue_t *,queue_t *);
+
+
+
+
+#endif
diff --git a/libupgrade/util.c b/libupgrade/util.c
new file mode 100644
index 0000000..9fa5b7a
--- /dev/null
+++ b/libupgrade/util.c
@@ -0,0 +1,715 @@
+
+/********************************************************************
+ * Workfile : util.c
+ * Project : Kraken
+ * Author : khwoo
+ * Description: Commands Template
+ *
+ * Copyright (c) 2009 HUMAX Co., Ltd.
+ * All rights reserved.
+ ********************************************************************/
+
+#define _______________________________________________________________________
+#define ____HEADER_FILES____
+#include "htype.h"
+#include "util.h"
+
+#define _______________________________________________________________________
+#define ____MACRO_DEFINITION____
+
+
+#define _______________________________________________________________________
+#define ____EXTERNAL_VARIABLE_DEFINITION____
+
+
+#define _______________________________________________________________________
+#define ____EXTERNAL_FUNCTION_DEFINITION____
+
+
+#define _______________________________________________________________________
+#define ____TYPE_DEFINITION____
+
+
+#define _______________________________________________________________________
+#define ____GLOBAL_VARIABLE_DEFINITION____
+
+
+#define _______________________________________________________________________
+#define ____STATIC_VARIABLE_DEFINITION____
+const static unsigned short CRC_16_TABLE[256] =
+{
+ 0x0000, 0xc0c1, 0xc181, 0x0140, 0xc301, 0x03c0, 0x0280, 0xc241,
+ 0xc601, 0x06c0, 0x0780, 0xc741, 0x0500, 0xc5c1, 0xc481, 0x0440,
+ 0xcc01, 0x0cc0, 0x0d80, 0xcd41, 0x0f00, 0xcfc1, 0xce81, 0x0e40,
+ 0x0a00, 0xcac1, 0xcb81, 0x0b40, 0xc901, 0x09c0, 0x0880, 0xc841,
+ 0xd801, 0x18c0, 0x1980, 0xd941, 0x1b00, 0xdbc1, 0xda81, 0x1a40,
+ 0x1e00, 0xdec1, 0xdf81, 0x1f40, 0xdd01, 0x1dc0, 0x1c80, 0xdc41,
+ 0x1400, 0xd4c1, 0xd581, 0x1540, 0xd701, 0x17c0, 0x1680, 0xd641,
+ 0xd201, 0x12c0, 0x1380, 0xd341, 0x1100, 0xd1c1, 0xd081, 0x1040,
+ 0xf001, 0x30c0, 0x3180, 0xf141, 0x3300, 0xf3c1, 0xf281, 0x3240,
+ 0x3600, 0xf6c1, 0xf781, 0x3740, 0xf501, 0x35c0, 0x3480, 0xf441,
+ 0x3c00, 0xfcc1, 0xfd81, 0x3d40, 0xff01, 0x3fc0, 0x3e80, 0xfe41,
+ 0xfa01, 0x3ac0, 0x3b80, 0xfb41, 0x3900, 0xf9c1, 0xf881, 0x3840,
+ 0x2800, 0xe8c1, 0xe981, 0x2940, 0xeb01, 0x2bc0, 0x2a80, 0xea41,
+ 0xee01, 0x2ec0, 0x2f80, 0xef41, 0x2d00, 0xedc1, 0xec81, 0x2c40,
+ 0xe401, 0x24c0, 0x2580, 0xe541, 0x2700, 0xe7c1, 0xe681, 0x2640,
+ 0x2200, 0xe2c1, 0xe381, 0x2340, 0xe101, 0x21c0, 0x2080, 0xe041,
+ 0xa001, 0x60c0, 0x6180, 0xa141, 0x6300, 0xa3c1, 0xa281, 0x6240,
+ 0x6600, 0xa6c1, 0xa781, 0x6740, 0xa501, 0x65c0, 0x6480, 0xa441,
+ 0x6c00, 0xacc1, 0xad81, 0x6d40, 0xaf01, 0x6fc0, 0x6e80, 0xae41,
+ 0xaa01, 0x6ac0, 0x6b80, 0xab41, 0x6900, 0xa9c1, 0xa881, 0x6840,
+ 0x7800, 0xb8c1, 0xb981, 0x7940, 0xbb01, 0x7bc0, 0x7a80, 0xba41,
+ 0xbe01, 0x7ec0, 0x7f80, 0xbf41, 0x7d00, 0xbdc1, 0xbc81, 0x7c40,
+ 0xb401, 0x74c0, 0x7580, 0xb541, 0x7700, 0xb7c1, 0xb681, 0x7640,
+ 0x7200, 0xb2c1, 0xb381, 0x7340, 0xb101, 0x71c0, 0x7080, 0xb041,
+ 0x5000, 0x90c1, 0x9181, 0x5140, 0x9301, 0x53c0, 0x5280, 0x9241,
+ 0x9601, 0x56c0, 0x5780, 0x9741, 0x5500, 0x95c1, 0x9481, 0x5440,
+ 0x9c01, 0x5cc0, 0x5d80, 0x9d41, 0x5f00, 0x9fc1, 0x9e81, 0x5e40,
+ 0x5a00, 0x9ac1, 0x9b81, 0x5b40, 0x9901, 0x59c0, 0x5880, 0x9841,
+ 0x8801, 0x48c0, 0x4980, 0x8941, 0x4b00, 0x8bc1, 0x8a81, 0x4a40,
+ 0x4e00, 0x8ec1, 0x8f81, 0x4f40, 0x8d01, 0x4dc0, 0x4c80, 0x8c41,
+ 0x4400, 0x84c1, 0x8581, 0x4540, 0x8701, 0x47c0, 0x4680, 0x8641,
+ 0x8201, 0x42c0, 0x4380, 0x8341, 0x4100, 0x81c1, 0x8081, 0x4040
+};
+
+const static unsigned long _crc32Tbl[256] =
+{
+ 0x00000000, 0x77073096, 0xee0e612c, 0x990951ba,
+ 0x076dc419, 0x706af48f, 0xe963a535, 0x9e6495a3,
+ 0x0edb8832, 0x79dcb8a4, 0xe0d5e91e, 0x97d2d988,
+ 0x09b64c2b, 0x7eb17cbd, 0xe7b82d07, 0x90bf1d91,
+ 0x1db71064, 0x6ab020f2, 0xf3b97148, 0x84be41de,
+ 0x1adad47d, 0x6ddde4eb, 0xf4d4b551, 0x83d385c7,
+ 0x136c9856, 0x646ba8c0, 0xfd62f97a, 0x8a65c9ec,
+ 0x14015c4f, 0x63066cd9, 0xfa0f3d63, 0x8d080df5,
+ 0x3b6e20c8, 0x4c69105e, 0xd56041e4, 0xa2677172,
+ 0x3c03e4d1, 0x4b04d447, 0xd20d85fd, 0xa50ab56b,
+ 0x35b5a8fa, 0x42b2986c, 0xdbbbc9d6, 0xacbcf940,
+ 0x32d86ce3, 0x45df5c75, 0xdcd60dcf, 0xabd13d59,
+ 0x26d930ac, 0x51de003a, 0xc8d75180, 0xbfd06116,
+ 0x21b4f4b5, 0x56b3c423, 0xcfba9599, 0xb8bda50f,
+ 0x2802b89e, 0x5f058808, 0xc60cd9b2, 0xb10be924,
+ 0x2f6f7c87, 0x58684c11, 0xc1611dab, 0xb6662d3d,
+ 0x76dc4190, 0x01db7106, 0x98d220bc, 0xefd5102a,
+ 0x71b18589, 0x06b6b51f, 0x9fbfe4a5, 0xe8b8d433,
+ 0x7807c9a2, 0x0f00f934, 0x9609a88e, 0xe10e9818,
+ 0x7f6a0dbb, 0x086d3d2d, 0x91646c97, 0xe6635c01,
+ 0x6b6b51f4, 0x1c6c6162, 0x856530d8, 0xf262004e,
+ 0x6c0695ed, 0x1b01a57b, 0x8208f4c1, 0xf50fc457,
+ 0x65b0d9c6, 0x12b7e950, 0x8bbeb8ea, 0xfcb9887c,
+ 0x62dd1ddf, 0x15da2d49, 0x8cd37cf3, 0xfbd44c65,
+ 0x4db26158, 0x3ab551ce, 0xa3bc0074, 0xd4bb30e2,
+ 0x4adfa541, 0x3dd895d7, 0xa4d1c46d, 0xd3d6f4fb,
+ 0x4369e96a, 0x346ed9fc, 0xad678846, 0xda60b8d0,
+ 0x44042d73, 0x33031de5, 0xaa0a4c5f, 0xdd0d7cc9,
+ 0x5005713c, 0x270241aa, 0xbe0b1010, 0xc90c2086,
+ 0x5768b525, 0x206f85b3, 0xb966d409, 0xce61e49f,
+ 0x5edef90e, 0x29d9c998, 0xb0d09822, 0xc7d7a8b4,
+ 0x59b33d17, 0x2eb40d81, 0xb7bd5c3b, 0xc0ba6cad,
+ 0xedb88320, 0x9abfb3b6, 0x03b6e20c, 0x74b1d29a,
+ 0xead54739, 0x9dd277af, 0x04db2615, 0x73dc1683,
+ 0xe3630b12, 0x94643b84, 0x0d6d6a3e, 0x7a6a5aa8,
+ 0xe40ecf0b, 0x9309ff9d, 0x0a00ae27, 0x7d079eb1,
+ 0xf00f9344, 0x8708a3d2, 0x1e01f268, 0x6906c2fe,
+ 0xf762575d, 0x806567cb, 0x196c3671, 0x6e6b06e7,
+ 0xfed41b76, 0x89d32be0, 0x10da7a5a, 0x67dd4acc,
+ 0xf9b9df6f, 0x8ebeeff9, 0x17b7be43, 0x60b08ed5,
+ 0xd6d6a3e8, 0xa1d1937e, 0x38d8c2c4, 0x4fdff252,
+ 0xd1bb67f1, 0xa6bc5767, 0x3fb506dd, 0x48b2364b,
+ 0xd80d2bda, 0xaf0a1b4c, 0x36034af6, 0x41047a60,
+ 0xdf60efc3, 0xa867df55, 0x316e8eef, 0x4669be79,
+ 0xcb61b38c, 0xbc66831a, 0x256fd2a0, 0x5268e236,
+ 0xcc0c7795, 0xbb0b4703, 0x220216b9, 0x5505262f,
+ 0xc5ba3bbe, 0xb2bd0b28, 0x2bb45a92, 0x5cb36a04,
+ 0xc2d7ffa7, 0xb5d0cf31, 0x2cd99e8b, 0x5bdeae1d,
+ 0x9b64c2b0, 0xec63f226, 0x756aa39c, 0x026d930a,
+ 0x9c0906a9, 0xeb0e363f, 0x72076785, 0x05005713,
+ 0x95bf4a82, 0xe2b87a14, 0x7bb12bae, 0x0cb61b38,
+ 0x92d28e9b, 0xe5d5be0d, 0x7cdcefb7, 0x0bdbdf21,
+ 0x86d3d2d4, 0xf1d4e242, 0x68ddb3f8, 0x1fda836e,
+ 0x81be16cd, 0xf6b9265b, 0x6fb077e1, 0x18b74777,
+ 0x88085ae6, 0xff0f6a70, 0x66063bca, 0x11010b5c,
+ 0x8f659eff, 0xf862ae69, 0x616bffd3, 0x166ccf45,
+ 0xa00ae278, 0xd70dd2ee, 0x4e048354, 0x3903b3c2,
+ 0xa7672661, 0xd06016f7, 0x4969474d, 0x3e6e77db,
+ 0xaed16a4a, 0xd9d65adc, 0x40df0b66, 0x37d83bf0,
+ 0xa9bcae53, 0xdebb9ec5, 0x47b2cf7f, 0x30b5ffe9,
+ 0xbdbdf21c, 0xcabac28a, 0x53b39330, 0x24b4a3a6,
+ 0xbad03605, 0xcdd70693, 0x54de5729, 0x23d967bf,
+ 0xb3667a2e, 0xc4614ab8, 0x5d681b02, 0x2a6f2b94,
+ 0xb40bbe37, 0xc30c8ea1, 0x5a05df1b, 0x2d02ef8d,
+}; /* _crc32Tbl */
+
+#define N_BIT_Byte 8
+#define SIZE_BitBuf (N_BIT_Byte * sizeof(_bitBuf))
+#define N_BIT_Dic 13
+#define SIZE_Dic (1 << N_BIT_Dic)
+#define MAX_Match 256
+#define THRESHOLD 3
+#define MAX_ByteNum 255
+#define NC (MAX_ByteNum + MAX_Match+2-THRESHOLD)
+#define N_BIT_C 9
+#define N_BIT_Code 16
+
+
+#define NP (N_BIT_Dic+1)
+#define NT (N_BIT_Code+3)
+#define PBIT 4 // smallest integer such that (1U<<PBIT) > NP
+#define TBIT 5 // smallest integer such that (1U<<TBIT) > NT
+#if NT>NP
+ #define NPT NT
+#else
+ #define NPT NP
+#endif
+
+extern unsigned long _compDataSize ; // compressed data size
+extern unsigned long _orgDataSize ; // original data size
+extern unsigned char _decompBuf[0x8000] ; // decompress buffer
+
+unsigned char _cLen[NC], _ptLen[NPT + 100], *_orgData, _dicBuf[SIZE_Dic];
+unsigned short _left[2*NC-1], _right[2*NC-1], _blkSize, _cTbl[4096],
+ _ptTbl[256], _bitBuf, _subBitBuf,
+ _start[18], _count[17], _weight[17];
+short _bitCount;
+unsigned short _compSize;
+
+
+#define _______________________________________________________________________
+#define ____STATIC_FUNCTION_DEFINITION____
+
+
+#define _______________________________________________________________________
+#define ____STATIC_FUNCTION_BODY____
+
+
+#define _______________________________________________________________________
+#define ____GLOBAL_FUNCTION_BODY____
+
+unsigned short GetCRC16(unsigned char *BufferPtr, unsigned long NumberOfByte)
+{
+ unsigned short CRC ;
+
+ CRC = 0;
+ while (NumberOfByte--)
+ {
+ CRC = (CRC >> 8) ^ CRC_16_TABLE[(CRC ^ *BufferPtr++) & 0xff] ;
+ }
+
+ return CRC ;
+} /* GetCrc16 */
+
+unsigned short GetCRC16Fast(void *inP, unsigned long NumberOfByte)
+{
+ unsigned short CRC ;
+ unsigned long *aligned_4;
+ unsigned long pre_count, end_count,loop_4;
+ unsigned long data;
+ unsigned char *BufferPtr = inP;
+
+ if (NumberOfByte < 4)
+ {
+ return GetCRC16(inP, NumberOfByte);
+ }
+ pre_count = ((unsigned long)BufferPtr & 0x03);
+ if(pre_count!=0)
+ pre_count = 4-pre_count;
+ aligned_4 = (unsigned long *)((unsigned long)BufferPtr + pre_count);
+ loop_4 = (NumberOfByte-pre_count)>>2;
+ end_count = NumberOfByte-(loop_4<<2)-pre_count;
+
+ CRC=0;
+ while((pre_count--)!=0)
+ {
+ CRC = (CRC >> 8) ^ CRC_16_TABLE[(CRC ^ *BufferPtr++) & 0xff] ;
+ }
+
+ BufferPtr=(unsigned char *)aligned_4+(loop_4<<2);
+
+ while((loop_4--)!=0)
+ {
+ data= *aligned_4++;
+#if defined(CONFIG_BIG_ENDIAN)
+ CRC = (CRC >> 8) ^ CRC_16_TABLE[(CRC ^ (data>>24)) & 0xff];
+ CRC = (CRC >> 8) ^ CRC_16_TABLE[(CRC ^ (data>>16)) & 0xff];
+ CRC = (CRC >> 8) ^ CRC_16_TABLE[(CRC ^ (data>> 8)) & 0xff];
+ CRC = (CRC >> 8) ^ CRC_16_TABLE[(CRC ^ (data )) & 0xff];
+#else
+ CRC = (CRC >> 8) ^ CRC_16_TABLE[(CRC ^ (data )) & 0xff];
+ CRC = (CRC >> 8) ^ CRC_16_TABLE[(CRC ^ (data>> 8)) & 0xff];
+ CRC = (CRC >> 8) ^ CRC_16_TABLE[(CRC ^ (data>>16)) & 0xff];
+ CRC = (CRC >> 8) ^ CRC_16_TABLE[(CRC ^ (data>>24)) & 0xff];
+#endif
+ }
+
+ while((end_count--)!=0)
+ {
+ CRC = (CRC >> 8) ^ CRC_16_TABLE[(CRC ^ *BufferPtr++) & 0xff];
+ }
+
+ return CRC ;
+
+} /* GetCrc16 */
+
+unsigned long GetCrc32(unsigned char *p, unsigned long n)
+{
+ unsigned long crc, *tbl;
+ unsigned long len;
+
+ len = n;
+
+ crc = 0xFFFFFFFF;
+ tbl = (unsigned long*)_crc32Tbl;
+ while (n--)
+ {
+ crc = (crc >> 8) ^ tbl[(crc ^ *p) & 0xff];
+ p++;
+ }
+ return ~crc;
+} /* GetCrc32 */
+
+unsigned long GetCRC32Fast(void *inP, unsigned long NumberOfByte)
+{
+ register unsigned long CRC ;
+ unsigned long *aligned_4;
+ unsigned long pre_count, end_count,loop_4;
+ unsigned long data;
+ unsigned char *BufferPtr = inP;
+
+ if (NumberOfByte < 4)
+ {
+ return GetCrc32(inP, NumberOfByte);
+ }
+ pre_count = ((unsigned long)BufferPtr & 0x03);
+ if(pre_count!=0)
+ pre_count = 4-pre_count;
+ aligned_4 = (unsigned long *)((unsigned long)BufferPtr + pre_count);
+ loop_4 = (NumberOfByte-pre_count)>>2;
+ end_count = NumberOfByte-(loop_4<<2)-pre_count;
+
+ CRC = 0xFFFFFFFF;
+ while((pre_count--)!=0)
+ {
+ CRC = (CRC >> 8) ^ _crc32Tbl[(CRC ^ *BufferPtr++) & 0xff] ;
+ }
+
+ BufferPtr=(unsigned char *)aligned_4+(loop_4<<2);
+
+ while((loop_4--)!=0)
+ {
+ data= *aligned_4++;
+#if defined(CONFIG_BIG_ENDIAN)
+ CRC = (CRC >> 8) ^ _crc32Tbl[(CRC ^ (data>>24)) & 0xff];
+ CRC = (CRC >> 8) ^ _crc32Tbl[(CRC ^ (data>>16)) & 0xff];
+ CRC = (CRC >> 8) ^ _crc32Tbl[(CRC ^ (data>> 8)) & 0xff];
+ CRC = (CRC >> 8) ^ _crc32Tbl[(CRC ^ (data )) & 0xff];
+#else
+ CRC = (CRC >> 8) ^ _crc32Tbl[(CRC ^ (data )) & 0xff];
+ CRC = (CRC >> 8) ^ _crc32Tbl[(CRC ^ (data>> 8)) & 0xff];
+ CRC = (CRC >> 8) ^ _crc32Tbl[(CRC ^ (data>>16)) & 0xff];
+ CRC = (CRC >> 8) ^ _crc32Tbl[(CRC ^ (data>>24)) & 0xff];
+#endif
+ }
+
+ while((end_count--)!=0)
+ {
+ CRC = (CRC >> 8) ^ _crc32Tbl[(CRC ^ *BufferPtr++) & 0xff] ;
+ }
+
+ return ~CRC ;
+
+} /* GetCrc16 */
+
+
+unsigned short Get12Bits(unsigned char * base)
+{
+ unsigned short temp = 0 ;
+
+ temp |= *(base + 0) ;
+ temp <<= 8 ;
+ temp |= *(base + 1) ;
+
+ return temp & 0x0FFF ;
+} /* Get12Bits */
+
+unsigned short Get16Bits(unsigned char *base)
+{
+ unsigned short temp = 0 ;
+
+ temp |= *(base + 0) ;
+ temp <<= 8 ;
+ temp |= *(base + 1) ;
+
+ return temp ;
+} /* Get16Bits */
+
+unsigned long Get24Bits(unsigned char *base)
+{
+ unsigned long temp = 0 ;
+
+ temp |= *(base + 0) ;
+ temp <<= 8 ;
+ temp |= *(base + 1) ;
+ temp <<= 8 ;
+ temp |= *(base + 2) ;
+
+ return temp ;
+} /* Get24Bits */
+
+unsigned long Get32Bits(unsigned char *base)
+{
+ unsigned long temp = 0 ;
+
+ temp |= *(base + 0) ;
+ temp <<= 8 ;
+ temp |= *(base + 1) ;
+ temp <<= 8 ;
+ temp |= *(base + 2) ;
+ temp <<= 8 ;
+ temp |= *(base + 3) ;
+
+ return temp ;
+} /* Get32Bits */
+
+unsigned short SWAP16(unsigned short A)
+{
+ return (((A >> 8) | (A << 8)));
+}
+
+unsigned int SWAP32(unsigned long A)
+{
+ return ((A << 24) | ((A << 8) & 0xFF0000) | ((A >> 8) & 0xFF00) |(A >> 24));
+}
+
+void MakeTbl(unsigned short nChar, unsigned char *bitLen, unsigned short tblBits, unsigned short *tbl)
+{
+ unsigned short *wp, *wpp, *wppp, i, k, avail, mask;
+ unsigned short len, ch, jutBits, nextCode;
+ unsigned char *bp;
+
+ for (wp=&_count[1],i=1; i<=16; i++)
+ *wp++ = 0;
+ for (wp=_count, bp=bitLen, i=0; i<nChar; i++)
+ wp[*bp++]++;
+
+ for (wp=&_start[1],wpp=&_count[1],*wp=0,i=1,k=15; i<=16; i++,k--,wp++)
+ wp[1] = *wp + (*wpp++ << k);
+
+ if (_start[17] != (unsigned short)(1U << 16))
+ printf("\n\nDecompression error: BAD TABLE\r\n\r\n");
+
+ jutBits = 16-tblBits;
+
+ for (wp=&_start[1],wpp=&_weight[1],i=1,k=tblBits-1; i<=tblBits; i++,k--)
+ {
+ *wp >>= jutBits;
+ wp++;
+ *wpp++ = 1U << k;
+ }
+
+ for (k=16-i,wp=&_weight[i]; i<=16; i++,k--)
+ *wp++ = 1U << k;
+
+ i = _start[tblBits+1] >> jutBits;
+ if (i != (unsigned short)(1U << 16))
+ {
+ k = 1U << tblBits;
+ while (i!=k)
+ tbl[i++] = 0;
+ }
+
+ avail = nChar;
+ mask = 1U << (15-tblBits);
+ wpp = _right;
+ wppp = _left;
+ for (ch=0,bp=bitLen; ch<nChar; ch++)
+ {
+ if ((len = *bp++) == 0)
+ continue;
+
+ k = _start[len];
+ nextCode = k + _weight[len];
+
+ if (len <= tblBits)
+ {
+ for (wp=tbl+k; k<nextCode; k++)
+ *wp++ = ch;
+ }
+ else
+ {
+ wp = tbl + (k >> jutBits);
+ i = len-tblBits;
+ while (i != 0)
+ {
+ if (*wp == 0)
+ {
+ wpp[avail] = wppp[avail] = 0;
+ *wp = avail++;
+ }
+ wp = (k&mask ? wpp : wppp) + *wp;
+ k <<= 1;
+ i--;
+ }
+ *wp = ch;
+ }
+ _start[len] = nextCode;
+ }
+} /* MakeTbl */
+
+
+void FillBuf(unsigned short n) /* Shift _bitBuf n bits left, read n bits */
+{
+ _bitBuf <<= n;
+ while (n > _bitCount)
+ {
+ n -= _bitCount;
+ _bitBuf |= _subBitBuf << n;
+ if (_compSize != 0)
+ {
+ _compSize--;
+ _subBitBuf = *_orgData++;
+ }
+ else
+ _subBitBuf = 0;
+ _bitCount = N_BIT_Byte;
+ }
+ _bitCount -= n;
+ _bitBuf |= _subBitBuf >> _bitCount;
+} /* FillBuf */
+
+
+unsigned short GetBits(unsigned short n)
+{
+ unsigned short x;
+
+ x = _bitBuf >> (SIZE_BitBuf-n);
+ FillBuf(n);
+
+ return x;
+} /* GetBits */
+
+
+void ReadPtLen(signed short nn, signed short nBit, signed short iSpecial)
+{
+ signed short i,c,n;
+ unsigned short mask, *wp;
+ unsigned char *bp;
+
+ n = GetBits(nBit);
+ if (n == 0)
+ {
+ c = GetBits(nBit);
+
+ for (bp=_ptLen,i=0; i<nn; i++)
+ *bp++ = 0;
+ for (wp=_ptTbl,i=0; i<256; i++)
+ *wp++ = c;
+ }
+ else
+ {
+ i = 0;
+ bp = _ptLen;
+ while (i < n)
+ {
+ c = _bitBuf >> (SIZE_BitBuf-3);
+ if (c == 7)
+ {
+ mask = 1U << (SIZE_BitBuf-1-3);
+ while (mask & _bitBuf)
+ {
+ mask >>= 1;
+ c++;
+ }
+ }
+ FillBuf(c<7 ? 3 : c-3);
+ bp[i++] = (unsigned char)c;
+ if (i == iSpecial)
+ {
+ c = GetBits(2);
+ while (--c >= 0)
+ bp[i++] = 0;
+ }
+ }
+ while (i<nn)
+ bp[i++] = 0;
+ MakeTbl(nn, bp, 8, _ptTbl);
+ }
+} /* ReadPtLen */
+
+
+void ReadCLen(void)
+{
+ signed short i, c, n;
+ unsigned short mask, *wp, *wpp;
+ unsigned char *bp, *bpp;
+
+ n = GetBits(N_BIT_C);
+ bp = _cLen;
+ if (n == 0)
+ {
+ c = GetBits(N_BIT_C);
+ for (i=0; i<NC; i++)
+ *bp++ = 0;
+ for (wp=_cTbl,i=0; i<4096; i++)
+ *wp++ = c;
+ }
+ else
+ {
+ i = 0;
+ bpp = _ptLen;
+ wp = _right;
+ wpp = _left;
+ while (i < n)
+ {
+ c = _ptTbl[_bitBuf>>(SIZE_BitBuf-8)];
+ if (c >= NT)
+ {
+ mask = 1U << (SIZE_BitBuf-1-8);
+ do
+ {
+ c = (_bitBuf & mask) ? wp[c] : wpp[c];
+ mask >>= 1;
+ } while (c >= NT);
+ }
+ FillBuf(bpp[c]);
+ if (c <= 2)
+ {
+ if (c == 0) c = 1;
+ else if (c == 1) c = GetBits(4) + 3;
+ else c = GetBits(N_BIT_C) + 20;
+
+ while (--c >= 0)
+ bp[i++]=0;
+ }
+ else
+ bp[i++] = c-2;
+ }
+ while (i < NC)
+ bp[i++] = 0;
+ MakeTbl(NC, bp, 12, _cTbl);
+ }
+} /* ReadCLen */
+
+
+unsigned short DecodeC(void)
+{
+ unsigned short i, mask, *wp, *wpp;
+
+ if (_blkSize == 0)
+ {
+ _blkSize = GetBits(16);
+ ReadPtLen(NT, TBIT, 3);
+ ReadCLen();
+ ReadPtLen(NP, PBIT, (unsigned short)-1);
+ }
+ _blkSize--;
+ i = _cTbl[_bitBuf >> (SIZE_BitBuf-12)];
+ if (i >= NC)
+ {
+ mask = 1U << (SIZE_BitBuf-1-12);
+ wp = _right;
+ wpp = _left;
+ do
+ {
+ i = (_bitBuf & mask) ? wp[i] : wpp[i];
+ mask >>= 1;
+ } while (i >= NC);
+ }
+ FillBuf(_cLen[i]);
+
+ return i;
+} /* DecodeC */
+
+
+unsigned short DecodeP(void)
+{
+ unsigned short i, mask, *wp, *wpp;
+
+ i = _ptTbl[_bitBuf >> (SIZE_BitBuf-8)];
+ if (i >= NP)
+ {
+ mask = 1U << (SIZE_BitBuf-1-8);
+ wp = _right;
+ wpp = _left;
+ do
+ {
+ i = (_bitBuf & mask) ? wp[i] : wpp[i];
+ mask >>= 1;
+ } while (i >= NP);
+ }
+ FillBuf(_ptLen[i]);
+ if (i != 0)
+ i = (1U << (i-1)) + GetBits(i-1);
+
+ return i;
+} /* DecodeP */
+
+
+unsigned char *DecompressData(unsigned char *data)
+{
+ signed short rem, n, i, r, c; // rem: remaining unsigned chars to copy
+ unsigned char *dicBuf, *decompBuf;
+ unsigned short orgSize;
+
+ _orgData = data;
+ orgSize = (unsigned short)_orgDataSize;
+ _compSize = (unsigned short)_compDataSize;
+ decompBuf = _decompBuf;
+
+ _bitBuf = _subBitBuf = 0;
+ _bitCount = 0;
+ FillBuf(SIZE_BitBuf);
+ _blkSize = 0;
+ rem = 0;
+ i = 0;
+
+ while (orgSize != 0)
+ {
+ dicBuf = _dicBuf;
+
+ n = (orgSize > SIZE_Dic) ? SIZE_Dic : orgSize;
+
+ r = 0;
+ while (--rem >= 0)
+ {
+ dicBuf[r] = dicBuf[i];
+ i = (i+1) & (SIZE_Dic-1);
+ if (++r == n)
+ goto NEXT;
+ }
+
+ while(1)
+ {
+ c = DecodeC();
+ if (c <= MAX_ByteNum)
+ {
+ dicBuf[r] = (unsigned char)c;
+ if (++r == n)
+ goto NEXT;
+ }
+ else
+ {
+ rem = c - (MAX_ByteNum+1-THRESHOLD);
+ i = (r-DecodeP()-1) & (SIZE_Dic-1);
+ while (--rem >= 0)
+ {
+ dicBuf[r] = dicBuf[i];
+ i = (i+1) & (SIZE_Dic-1);
+ if (++r == n)
+ goto NEXT;
+ }
+ }
+ }
+
+ NEXT:
+
+ for (r=0; r<n; r++)
+ *decompBuf++ = *dicBuf++;
+
+ orgSize -= n;
+ }
+
+// DSI_printf(0, "Decomp end\r\n");
+
+ return _decompBuf;
+} /* Decompress */
+
diff --git a/libupgrade/util.h b/libupgrade/util.h
new file mode 100644
index 0000000..d996f5e
--- /dev/null
+++ b/libupgrade/util.h
@@ -0,0 +1,50 @@
+
+#ifndef _UTIL_H_
+#define _UTIL_H_
+/********************************************************************
+ * Workfile : util.h
+ * Project : Kraken
+ * Author : khwoo
+ * Description: Commands Template
+ *
+ * Copyright (c) 2009 HUMAX Co., Ltd.
+ * All rights reserved.
+ ********************************************************************/
+
+#define _______________________________________________________________________
+#define ____HEADER_FILES____
+
+
+#define _______________________________________________________________________
+#define ____MACRO_DEFINITION____
+
+
+#define _______________________________________________________________________
+#define ____TYPE_DEFINITION____
+
+
+#define _______________________________________________________________________
+#define ____EXTERNAL_VARIABLE_DEFINITION____
+
+
+#define _______________________________________________________________________
+#define ____EXTERNAL_FUNCTION_DEFINITION____
+unsigned short GetCRC16(unsigned char *BufferPtr, unsigned long NumberOfByte);
+unsigned short GetCRC16Fast(void *inP, unsigned long NumberOfByte);
+unsigned long GetCrc32(unsigned char *p, unsigned long n);
+unsigned long GetCRC32Fast(void *inP, unsigned long NumberOfByte);
+unsigned short Get12Bits(unsigned char * base);
+unsigned short Get16Bits(unsigned char *base);
+unsigned long Get24Bits(unsigned char *base);
+unsigned long Get32Bits(unsigned char *base);
+unsigned short SWAP16(unsigned short A);
+unsigned int SWAP32(unsigned long A);
+
+unsigned char *DecompressData(unsigned char *data);
+
+//long atol(const char *dest);
+//char tolower(char c);
+
+#endif /* _UTIL_H_ */
+
+