Project reconstructed && Fix speed issue caused by excessive IO frequency && New information and progress bar output
This commit is contained in:
parent
2b17809d07
commit
e3571db925
2
.gitignore
vendored
Normal file
2
.gitignore
vendored
Normal file
@ -0,0 +1,2 @@
|
||||
Build/
|
||||
Test/
|
18
.vscode/c_cpp_properties.json
vendored
Normal file
18
.vscode/c_cpp_properties.json
vendored
Normal file
@ -0,0 +1,18 @@
|
||||
{
|
||||
"configurations": [
|
||||
{
|
||||
"name": "Win32",
|
||||
"includePath": [
|
||||
"${workspaceFolder}/Inc",
|
||||
"${workspaceFolder}/**"
|
||||
],
|
||||
"defines": [
|
||||
"UNICODE",
|
||||
"_UNICODE"
|
||||
],
|
||||
"cStandard": "c17",
|
||||
"cppStandard": "c++17"
|
||||
}
|
||||
],
|
||||
"version": 4
|
||||
}
|
18
.vscode/launch.json
vendored
Normal file
18
.vscode/launch.json
vendored
Normal file
@ -0,0 +1,18 @@
|
||||
{
|
||||
"version": "0.2.0",
|
||||
"configurations": [
|
||||
{
|
||||
"name": "[SNOOPerToCSV]构建并调试",
|
||||
"type": "cppdbg",
|
||||
"request": "launch",
|
||||
"preLaunchTask": "project_debug_build_task", // 预构建脚本
|
||||
"program": "${workspaceFolder}\\Build\\Debug\\SNOOPerToCSV.exe", // 调试目标
|
||||
"args": [ // 附加参数
|
||||
],
|
||||
"stopAtEntry": false,
|
||||
"cwd": "${workspaceFolder}", // 工作目录
|
||||
"environment": [],
|
||||
// "console": "externalTerminal",
|
||||
}
|
||||
]
|
||||
}
|
17
.vscode/tasks.json
vendored
Normal file
17
.vscode/tasks.json
vendored
Normal file
@ -0,0 +1,17 @@
|
||||
{
|
||||
"tasks": [
|
||||
{
|
||||
"label": "project_debug_build_task", //定义的Task标签
|
||||
"type": "shell", //Task执行的类型
|
||||
"options": {
|
||||
"cwd": "${workspaceFolder}" // 工作目录
|
||||
},
|
||||
"command": "make", //运行的命令
|
||||
"args": [ // 附加参数
|
||||
"debug",
|
||||
"-j4"
|
||||
],
|
||||
}
|
||||
],
|
||||
"version": "2.0.0"
|
||||
}
|
10
Inc/Config.hpp
Normal file
10
Inc/Config.hpp
Normal file
@ -0,0 +1,10 @@
|
||||
#ifndef __CONFIG_HPP__
|
||||
#define __CONFIG_HPP__
|
||||
|
||||
// 进度条长度
|
||||
#define PROGRESS_LENGTH 29
|
||||
|
||||
// 默认数值类型
|
||||
#define DEFAULT_VALUE_TYPE "uint64_t"
|
||||
|
||||
#endif
|
13
Inc/Global_Variables.hpp
Normal file
13
Inc/Global_Variables.hpp
Normal file
@ -0,0 +1,13 @@
|
||||
#ifndef __GLOBAL_VARIABLES_HPP__
|
||||
#define __GLOBAL_VARIABLES_HPP__
|
||||
|
||||
#include "Type_Descriptions.hpp"
|
||||
|
||||
// 文件列表
|
||||
extern file_node *file_list_head;
|
||||
// 值列表
|
||||
extern value_node *value_list_head;
|
||||
// 起始时间戳
|
||||
extern double time_begin;
|
||||
|
||||
#endif
|
25
Inc/Tool_Functions.hpp
Normal file
25
Inc/Tool_Functions.hpp
Normal file
@ -0,0 +1,25 @@
|
||||
#ifndef __TOOL_FUNCTIONS_HPP__
|
||||
#define __TOOL_FUNCTIONS_HPP__
|
||||
|
||||
#include "Config.hpp"
|
||||
|
||||
extern "C"
|
||||
{
|
||||
#include "stdint.h"
|
||||
#include "stdio.h"
|
||||
#include "stdbool.h"
|
||||
}
|
||||
|
||||
// 行进到上一行起始位置
|
||||
size_t f_seek_pre_line_begin(FILE *file);
|
||||
|
||||
// 读取文件一行
|
||||
size_t f_getline(FILE *file, char *buffer, const size_t buffer_len);
|
||||
|
||||
// 进度条打印
|
||||
void progress_print(size_t completed, size_t total, bool reflush);
|
||||
|
||||
// 16进制字符串转十进制数值(8字节)
|
||||
uint64_t hex_to_decimal(const char *str);
|
||||
|
||||
#endif
|
28
Inc/Type_Descriptions.hpp
Normal file
28
Inc/Type_Descriptions.hpp
Normal file
@ -0,0 +1,28 @@
|
||||
#ifndef __TYPE_DESCRIPTIONS_HPP__
|
||||
#define __TYPE_DESCRIPTIONS_HPP__
|
||||
|
||||
#include "Config.hpp"
|
||||
|
||||
extern "C"
|
||||
{
|
||||
#include "stdint.h"
|
||||
}
|
||||
|
||||
// 文件链表节点
|
||||
typedef struct file_node_struct
|
||||
{
|
||||
const char *file_name_str = nullptr;
|
||||
file_node_struct *p_next = nullptr;
|
||||
} file_node;
|
||||
|
||||
// 数据列表
|
||||
typedef struct value_node_struct
|
||||
{
|
||||
char value_name_str[100] = {'\0'};
|
||||
const char *value_type_str = "uint64_t";
|
||||
uint64_t raw_value = 0x0000000000000000;
|
||||
value_node_struct *p_next;
|
||||
} value_node;
|
||||
|
||||
// 数据类型
|
||||
#endif
|
223
Makefile
Normal file
223
Makefile
Normal file
@ -0,0 +1,223 @@
|
||||
# 目标文件名称
|
||||
TARGET_FILE_NAME = SNOOPerToCSV
|
||||
|
||||
# 编译目录
|
||||
BUILD_DIR = Build
|
||||
|
||||
# Release 编译子目录
|
||||
SUB_DIR_RELEASE = Release
|
||||
|
||||
# Debug 编译子目录
|
||||
SUB_DIR_DEBUG = Debug
|
||||
|
||||
# Release 优化等级
|
||||
RELEASE_OPT = -Os
|
||||
|
||||
# Debug 优化等级
|
||||
DEBUG_OPT = -O0
|
||||
|
||||
# GUI或CUI编译选项 [0]CUI/Console [1]GUI
|
||||
GUI = 0
|
||||
|
||||
# C编译标准
|
||||
C_STD = c17
|
||||
|
||||
# C++编译标准
|
||||
CXX_STD = c++17
|
||||
|
||||
# 源文件编码定义
|
||||
INPUT_CHAR_ENCODING = UTF-8
|
||||
|
||||
# 编译产物单字节字符(char)编码定义
|
||||
OUTPUT_CHAR_ENCODING = GBK
|
||||
|
||||
# 编译产物宽字符(wchar_t)编码定义
|
||||
OUTPUT_WCHAR_ENCODING = UTF-16LE
|
||||
|
||||
# 编译工具前缀
|
||||
COMPLIER_PREFIX = \
|
||||
|
||||
# C编译工具
|
||||
C_COMPLIER = $(strip $(COMPLIER_PREFIX))gcc
|
||||
|
||||
# C++编译工具
|
||||
C++_COMPLIER = $(strip $(COMPLIER_PREFIX))g++
|
||||
|
||||
# Windows 资源文件编译工具
|
||||
WIN_RES_COMPLIER = windres
|
||||
|
||||
##################################################################################
|
||||
|
||||
# 链接库
|
||||
LIB_LINK = \
|
||||
|
||||
# C定义
|
||||
C_DEFS = \
|
||||
_UNICODE \
|
||||
UNICODE \
|
||||
|
||||
# C头文件目录
|
||||
C_INCLUDES_PATHS = \
|
||||
|
||||
# C源文件目录
|
||||
C_SOURCES_PATHS = \
|
||||
|
||||
# C额外单个源文件
|
||||
C_EXTERA_SOURCES = \
|
||||
|
||||
# C++定义
|
||||
CXX_DEFS = \
|
||||
_UNICODE \
|
||||
UNICODE \
|
||||
|
||||
# C++ 头文件目录
|
||||
CXX_INCLUDES_PATHS = \
|
||||
Inc \
|
||||
|
||||
# C++源文件目录
|
||||
CXX_SOURCES_PATHS = \
|
||||
Src \
|
||||
|
||||
# C++额外单个源文件
|
||||
CXX_EXTERA_SOURCES = \
|
||||
|
||||
# Windows 资源文件脚本头文件路径
|
||||
WIN_RESOURCE_INCLUDES_PATHS = \
|
||||
|
||||
# Windows 资源文件脚本列表
|
||||
WIN_RESOURCE_SCRIPTS = \
|
||||
|
||||
##################################################################################
|
||||
|
||||
# C编译选项
|
||||
CFLAGS = $(foreach text,$(C_DEFS),$(addprefix -D,$(text))) \
|
||||
$(foreach path,$(C_INCLUDES_PATHS),$(addprefix -I,$(path))) \
|
||||
-std=$(strip $(C_STD)) \
|
||||
-finput-charset=$(strip $(INPUT_CHAR_ENCODING)) \
|
||||
-fexec-charset=$(strip $(OUTPUT_CHAR_ENCODING)) \
|
||||
-fwide-exec-charset=$(strip $(OUTPUT_WCHAR_ENCODING)) \
|
||||
-static \
|
||||
-Wall \
|
||||
-MMD -MP -MF"$(@:%.o=%.d)" \
|
||||
|
||||
# C++编译选项
|
||||
CXXFLAGS = $(foreach text,$(CXX_DEFS),$(addprefix -D,$(text))) \
|
||||
$(foreach path,$(CXX_INCLUDES_PATHS),$(addprefix -I,$(path))) \
|
||||
-std=$(strip $(CXX_STD)) \
|
||||
-finput-charset=$(strip $(INPUT_CHAR_ENCODING)) \
|
||||
-fexec-charset=$(strip $(OUTPUT_CHAR_ENCODING)) \
|
||||
-fwide-exec-charset=$(strip $(OUTPUT_WCHAR_ENCODING)) \
|
||||
-static \
|
||||
-Wall \
|
||||
-MMD -MP -MF"$(@:%.o=%.d)" \
|
||||
-lstdc++ \
|
||||
|
||||
# 链接选项
|
||||
LDFLAGS = -Wl,-Map,$(basename $@).map \
|
||||
|
||||
##################################################################################
|
||||
|
||||
# GUI与CUI选项附加
|
||||
ifeq ($(GUI), 1)
|
||||
LDFLAGS += -mwindows
|
||||
else
|
||||
LDFLAGS += -mconsole
|
||||
endif
|
||||
|
||||
# C目标文件及索引目录关联
|
||||
OBJECTS = $(notdir $(C_EXTERA_SOURCES:.c=.o))
|
||||
OBJECTS += $(subst .c,.o,$(notdir $(foreach path,$(C_SOURCES_PATHS),$(wildcard $(path)/*.c))))
|
||||
vpath %.c $(sort $(dir $(C_EXTERA_SOURCES))) $(sort $(C_SOURCES_PATHS))
|
||||
|
||||
# C++目标文件及索引目录关联
|
||||
OBJECTS += $(notdir $(CXX_EXTERA_SOURCES:.cpp=.o))
|
||||
OBJECTS += $(subst .cpp,.o,$(notdir $(foreach path,$(CXX_SOURCES_PATHS),$(wildcard $(path)/*.cpp))))
|
||||
vpath %.cpp $(sort $(dir $(CXX_EXTERA_SOURCES))) $(sort $(CXX_SOURCES_PATHS))
|
||||
|
||||
# Windows资源文件及索引目录关联
|
||||
OBJECTS += $(notdir $(WIN_RESOURCE_SCRIPTS:.rc=.o))
|
||||
vpath %.rc $(sort $(dir $(WIN_RESOURCE_SCRIPTS)))
|
||||
|
||||
|
||||
# Release 目标文件
|
||||
RELEASE_OBJECTS = $(addprefix $(BUILD_DIR)/$(SUB_DIR_RELEASE)/,$(OBJECTS))
|
||||
|
||||
# Debug 目标文件
|
||||
DEBUG_OBJECTS = $(addprefix $(BUILD_DIR)/$(SUB_DIR_DEBUG)/,$(OBJECTS))
|
||||
|
||||
##################################################################################
|
||||
|
||||
# all任务 目标为 release 和 debug 产物
|
||||
all: $(BUILD_DIR)/$(SUB_DIR_RELEASE)/$(TARGET_FILE_NAME).exe $(BUILD_DIR)/$(SUB_DIR_DEBUG)/$(TARGET_FILE_NAME).exe
|
||||
@echo ====== [All] Build Procedure Accomplished ======
|
||||
|
||||
# release任务 目标为 release 产物
|
||||
release: $(BUILD_DIR)/$(SUB_DIR_RELEASE)/$(TARGET_FILE_NAME).exe
|
||||
@echo ====== [Release] Build Procedure Accomplished ======
|
||||
|
||||
# debug任务 目标为 debug 产物
|
||||
debug: $(BUILD_DIR)/$(SUB_DIR_DEBUG)/$(TARGET_FILE_NAME).exe
|
||||
@echo ====== [Debug] Build Procedure Accomplished ======
|
||||
|
||||
# 清理任务
|
||||
clean: $(BUILD_DIR)
|
||||
powershell rm -r $(BUILD_DIR)
|
||||
|
||||
# 构建目录生成
|
||||
$(BUILD_DIR):
|
||||
powershell mkdir $@
|
||||
|
||||
# Release 工作目录生成
|
||||
$(BUILD_DIR)/$(SUB_DIR_RELEASE): | $(BUILD_DIR)
|
||||
powershell mkdir $@
|
||||
|
||||
# Debug 工作目录生成
|
||||
$(BUILD_DIR)/$(SUB_DIR_DEBUG): | $(BUILD_DIR)
|
||||
powershell mkdir $@
|
||||
|
||||
# Release 最终可执行文件编译任务
|
||||
$(BUILD_DIR)/$(SUB_DIR_RELEASE)/$(TARGET_FILE_NAME).exe: $(RELEASE_OBJECTS)
|
||||
@echo ====== [Release] All File Compiled. Now Linking... ======
|
||||
$(C++_COMPLIER) $(RELEASE_OBJECTS) -static -o $@ $(LIB_LINK) $(LDFLAGS)
|
||||
@echo ====== [Release] Program Link Finished ======
|
||||
|
||||
# Debug 最终可执行文件编译任务
|
||||
$(BUILD_DIR)/$(SUB_DIR_DEBUG)/$(TARGET_FILE_NAME).exe: $(DEBUG_OBJECTS)
|
||||
@echo ====== [Debug] All File Compiled. Now Linking... ======
|
||||
$(C++_COMPLIER) $(DEBUG_OBJECTS) -static -o $@ $(LIB_LINK) $(LDFLAGS)
|
||||
@echo ====== [Debug] Program Link Finished ======
|
||||
|
||||
# C Release 目标文件编译
|
||||
$(BUILD_DIR)/$(SUB_DIR_RELEASE)%.o: %.c Makefile | $(BUILD_DIR)/$(SUB_DIR_RELEASE)
|
||||
@echo ====== [Release] C Source File "$<" Compiling... ======
|
||||
$(C_COMPLIER) -c $(CFLAGS) $(RELEASE_OPT) -Wa,-a,-ad,-alms=$(BUILD_DIR)/$(SUB_DIR_RELEASE)/$(notdir $(<:.c=.lst)) $< -o $@
|
||||
|
||||
# C++ Release 目标文件编译
|
||||
$(BUILD_DIR)/$(SUB_DIR_RELEASE)/%.o: %.cpp Makefile | $(BUILD_DIR)/$(SUB_DIR_RELEASE)
|
||||
@echo ====== [Release] C++ Source File "$<" Compiling... ======
|
||||
$(C++_COMPLIER) -c $(CXXFLAGS) $(RELEASE_OPT) -Wa,-a,-ad,-ahlms=$(BUILD_DIR)/$(SUB_DIR_RELEASE)/$(notdir $(<:.cpp=.lst)) $< -o $@
|
||||
|
||||
# Release 资源脚本文件编译
|
||||
$(BUILD_DIR)/$(SUB_DIR_RELEASE)/%.o: %.rc Makefile | $(BUILD_DIR)/$(SUB_DIR_RELEASE)
|
||||
@echo ====== [Release] Windows Resource Script File "$<" Compiling... ======
|
||||
$(WIN_RES_COMPLIER) $(foreach path,$(WIN_RESOURCE_INCLUDES_PATHS),$(addprefix -I,$(path))) $< -o $@
|
||||
|
||||
# C Debug 目标文件编译
|
||||
$(BUILD_DIR)/$(SUB_DIR_DEBUG)%.o: %.c Makefile | $(BUILD_DIR)/$(SUB_DIR_DEBUG)
|
||||
@echo ====== [Debug] C Source File "$<" Compiling... ======
|
||||
$(C_COMPLIER) -c $(CFLAGS) $(DEBUG_OPT) -g -Wa,-a,-ad,-alms=$(BUILD_DIR)/$(SUB_DIR_DEBUG)/$(notdir $(<:.c=.lst)) $< -o $@
|
||||
|
||||
# C++ Debug 目标文件编译
|
||||
$(BUILD_DIR)/$(SUB_DIR_DEBUG)/%.o: %.cpp Makefile | $(BUILD_DIR)/$(SUB_DIR_DEBUG)
|
||||
@echo ====== [Debug] C++ Source File "$<" Compiling... ======
|
||||
$(C++_COMPLIER) -c $(CXXFLAGS) $(DEBUG_OPT) -g -Wa,-a,-ad,-ahlms=$(BUILD_DIR)/$(SUB_DIR_DEBUG)/$(notdir $(<:.cpp=.lst)) $< -o $@
|
||||
|
||||
# Debug 资源脚本文件编译
|
||||
$(BUILD_DIR)/$(SUB_DIR_DEBUG)/%.o: %.rc Makefile | $(BUILD_DIR)/$(SUB_DIR_DEBUG)
|
||||
@echo ====== [Debug] Windows Resource Script File "$<" Compiling... ======
|
||||
$(WIN_RES_COMPLIER) $(foreach path,$(WIN_RESOURCE_INCLUDES_PATHS),$(addprefix -I,$(path))) $< -o $@
|
||||
|
||||
|
||||
# 依赖关系
|
||||
-include $(RELEASE_OBJECTS:.o=.d)
|
||||
-include $(DEBUG_OBJECTS:.o=.d)
|
8
Src/Global_Variables.cpp
Normal file
8
Src/Global_Variables.cpp
Normal file
@ -0,0 +1,8 @@
|
||||
#include "Global_Variables.hpp"
|
||||
|
||||
// 文件列表
|
||||
file_node *file_list_head = nullptr;
|
||||
// 值列表
|
||||
value_node *value_list_head = nullptr;
|
||||
// 起始时间戳
|
||||
double time_begin = 0.0;
|
@ -1,3 +1,6 @@
|
||||
#include "Tool_Functions.hpp"
|
||||
#include "Global_Variables.hpp"
|
||||
|
||||
extern "C"
|
||||
{
|
||||
#include "stdio.h"
|
||||
@ -7,117 +10,6 @@ extern "C"
|
||||
#include "ctype.h"
|
||||
}
|
||||
|
||||
// 行进到上一行起始位置
|
||||
size_t f_seek_pre_line_begin(FILE *file)
|
||||
{
|
||||
int count = 0;
|
||||
|
||||
// 本身就在文件起始位置
|
||||
if (ftell(file) == 0)
|
||||
return 0;
|
||||
// 本身在文件结尾
|
||||
if (fgetc(file) == EOF)
|
||||
{
|
||||
// 移动到之前
|
||||
do
|
||||
{
|
||||
fseek(file, -2, SEEK_CUR);
|
||||
count--;
|
||||
} while (ftell(file) != 0 && fgetc(file) != '\n');
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
// 其它情况返
|
||||
|
||||
// 移动到上一行的结尾处
|
||||
while (ftell(file) != 0 && fgetc(file) != '\n')
|
||||
{
|
||||
fseek(file, -2, SEEK_CUR);
|
||||
count--;
|
||||
}
|
||||
|
||||
fseek(file, -2, SEEK_CUR);
|
||||
count--;
|
||||
|
||||
// 移动到上上一行的结尾处
|
||||
while (ftell(file) != 0 && fgetc(file) != '\n')
|
||||
{
|
||||
fseek(file, -2, SEEK_CUR);
|
||||
count--;
|
||||
}
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
// 读取一行
|
||||
size_t f_getline(FILE *file, char *buffer, size_t buffer_len)
|
||||
{
|
||||
memset(buffer, '\0', buffer_len);
|
||||
int count = 0;
|
||||
|
||||
while (true)
|
||||
{
|
||||
if (count >= buffer_len)
|
||||
{
|
||||
fseek(file, -count, SEEK_CUR);
|
||||
memset(buffer, '\0', buffer_len);
|
||||
return 0;
|
||||
}
|
||||
|
||||
char ch = fgetc(file);
|
||||
|
||||
if (ch == EOF && count == 0)
|
||||
return 0;
|
||||
if (ch == '\n' || ch == EOF)
|
||||
{
|
||||
buffer[count] = ch;
|
||||
return count + 1;
|
||||
}
|
||||
|
||||
buffer[count] = ch;
|
||||
count++;
|
||||
}
|
||||
}
|
||||
|
||||
// 16进制字符串转十进制数值(8字节)
|
||||
uint64_t hex_to_decimal(const char *str)
|
||||
{
|
||||
uint64_t value = 0;
|
||||
|
||||
int len = strlen(str);
|
||||
// 循环读取
|
||||
for (int count = 0; count < len; count++)
|
||||
{
|
||||
value *= 16;
|
||||
if (str[count] >= '0' && str[count] <= '9')
|
||||
value += str[count] - '0';
|
||||
else
|
||||
value += toupper(str[count]) - 'A' + 10;
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
// 文件链表节点
|
||||
typedef struct file_node_struct
|
||||
{
|
||||
const char *file_name_str = nullptr;
|
||||
file_node_struct *p_next = nullptr;
|
||||
} file_node;
|
||||
|
||||
// 数据列表
|
||||
typedef struct value_node_struct
|
||||
{
|
||||
char value_name_str[100] = {'\0'};
|
||||
uint64_t raw_value = 0x0000000000000000;
|
||||
value_node_struct *p_next;
|
||||
} value_node;
|
||||
|
||||
// 文件列表
|
||||
file_node *file_list_head = nullptr;
|
||||
value_node *value_list_head = nullptr;
|
||||
double time_begin = 0.0;
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
// 处理指令输入
|
||||
@ -136,6 +28,11 @@ int main(int argc, char *argv[])
|
||||
continue;
|
||||
}
|
||||
|
||||
// 处理格式串指令
|
||||
{
|
||||
}
|
||||
|
||||
// 其余输入作为文件输入
|
||||
static file_node *target_node = nullptr;
|
||||
if (file_list_head == nullptr)
|
||||
{
|
||||
@ -153,9 +50,11 @@ int main(int argc, char *argv[])
|
||||
target_node->p_next = nullptr;
|
||||
}
|
||||
target_node->file_name_str = argv[count];
|
||||
printf("%s\n", argv[count]);
|
||||
// printf("%s\n", argv[count]);
|
||||
}
|
||||
|
||||
printf("\n\n");
|
||||
|
||||
// 遍历文件
|
||||
file_node *target_file_node = file_list_head;
|
||||
while (target_file_node != nullptr)
|
||||
@ -171,14 +70,28 @@ int main(int argc, char *argv[])
|
||||
output_file = fopen(buffer, "wb");
|
||||
}
|
||||
|
||||
if (input_file == nullptr || output_file == nullptr)
|
||||
{
|
||||
target_file_node = target_file_node->p_next;
|
||||
continue;
|
||||
}
|
||||
|
||||
printf("Solving file: \"%s\"\n", target_file_node->file_name_str);
|
||||
printf("----------------------------------------------------------------\n");
|
||||
printf("%-40s %-16s %s\n", "Value Name", "Out Type", "ID");
|
||||
printf("----------------------------------------------------------------\n");
|
||||
|
||||
char segment_buffer[1000] = {'\0'};
|
||||
|
||||
size_t total_line;
|
||||
|
||||
// 跳过非数据行
|
||||
while (true)
|
||||
{
|
||||
f_getline(input_file, segment_buffer, sizeof(segment_buffer));
|
||||
if (segment_buffer[0] == '-')
|
||||
{
|
||||
sscanf(segment_buffer + 1, "%zu", &total_line);
|
||||
f_seek_pre_line_begin(input_file);
|
||||
break;
|
||||
}
|
||||
@ -189,6 +102,7 @@ int main(int argc, char *argv[])
|
||||
// 分配数值链表节点
|
||||
value_list_head = (value_node *)malloc(sizeof(value_node));
|
||||
value_list_head->p_next = nullptr;
|
||||
value_list_head->value_type_str = DEFAULT_VALUE_TYPE;
|
||||
value_list_head->raw_value = 0x0000000000000000;
|
||||
memset(value_list_head->value_name_str, '\0', sizeof(value_list_head->value_name_str));
|
||||
|
||||
@ -205,7 +119,7 @@ int main(int argc, char *argv[])
|
||||
value_list_head->raw_value = hex_to_decimal(value_str);
|
||||
}
|
||||
|
||||
// 处理第一个数值循环
|
||||
// 处理第一个数值循环记录
|
||||
{
|
||||
value_node *target_value_node = value_list_head;
|
||||
while (true)
|
||||
@ -222,18 +136,28 @@ int main(int argc, char *argv[])
|
||||
// 完成回环
|
||||
if (!strcmp(value_name_str, value_list_head->value_name_str))
|
||||
{
|
||||
// 回转到文件的第二行
|
||||
// 回转到文件的数据行起始位置
|
||||
memset(segment_buffer, '\0', sizeof(segment_buffer));
|
||||
fseek(input_file, 0, SEEK_SET);
|
||||
f_getline(input_file, segment_buffer, sizeof(segment_buffer));
|
||||
// 跳过非数据行
|
||||
while (true)
|
||||
{
|
||||
f_getline(input_file, segment_buffer, sizeof(segment_buffer));
|
||||
if (segment_buffer[0] == '-')
|
||||
{
|
||||
sscanf(segment_buffer + 1, "%zu", &total_line);
|
||||
f_seek_pre_line_begin(input_file);
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
// 未完成回环,记录新的类型
|
||||
// 分配数值链表节点
|
||||
// 未完成回环,分配数值链表节点
|
||||
target_value_node->p_next = (value_node *)malloc(sizeof(value_node));
|
||||
target_value_node = target_value_node->p_next;
|
||||
target_value_node->p_next = nullptr;
|
||||
target_value_node->value_type_str = DEFAULT_VALUE_TYPE;
|
||||
target_value_node->raw_value = 0x0000000000000000;
|
||||
memset(target_value_node->value_name_str, '\0', sizeof(target_value_node->value_name_str));
|
||||
|
||||
@ -243,6 +167,18 @@ int main(int argc, char *argv[])
|
||||
}
|
||||
}
|
||||
|
||||
// 展示数据类型输出
|
||||
{
|
||||
value_node *target_value_node = value_list_head;
|
||||
size_t value_count = 0;
|
||||
|
||||
while (target_value_node != nullptr)
|
||||
{
|
||||
printf("%-40s %-16s [%d]\n", target_value_node->value_name_str, target_value_node->value_type_str, value_count++);
|
||||
target_value_node = target_value_node->p_next;
|
||||
}
|
||||
}
|
||||
|
||||
// 输出csv抬头部分
|
||||
{
|
||||
value_node *target_value_node = value_list_head;
|
||||
@ -257,7 +193,10 @@ int main(int argc, char *argv[])
|
||||
|
||||
// 循环处理数据
|
||||
{
|
||||
printf("----------------------------------------------------------------\n");
|
||||
|
||||
memset(segment_buffer, '\0', sizeof(segment_buffer));
|
||||
size_t line_count = -1;
|
||||
while (f_getline(input_file, segment_buffer, sizeof(segment_buffer)) != 0)
|
||||
{
|
||||
char value_name_str[100] = {'\0'};
|
||||
@ -279,7 +218,10 @@ int main(int argc, char *argv[])
|
||||
timestamp += time;
|
||||
}
|
||||
|
||||
printf("timestamp: %lfs %s\n", timestamp, segment_buffer);
|
||||
line_count++;
|
||||
if ((line_count % 10000) == 0)
|
||||
progress_print(line_count, total_line, true);
|
||||
// printf("timestamp: %lfs %s\n", timestamp, segment_buffer);
|
||||
|
||||
// 处理数值链表
|
||||
value_node *target_value_node = value_list_head;
|
||||
@ -290,8 +232,15 @@ int main(int argc, char *argv[])
|
||||
if (!strcmp(value_name_str, target_value_node->value_name_str))
|
||||
target_value_node->raw_value = hex_to_decimal(value_str);
|
||||
|
||||
// 输出当前值
|
||||
fprintf(output_file, ",%d", target_value_node->raw_value + 0);
|
||||
// 特殊处理
|
||||
if (strstr(target_value_node->value_name_str, "wmrmeasured_speed"))
|
||||
{
|
||||
float *value = (float *)&(target_value_node->raw_value);
|
||||
fprintf(output_file, ",%f", *value);
|
||||
}
|
||||
else
|
||||
fprintf(output_file, ",%llu", target_value_node->raw_value);
|
||||
|
||||
target_value_node = target_value_node->p_next;
|
||||
}
|
||||
fprintf(output_file, "\n");
|
||||
@ -299,6 +248,13 @@ int main(int argc, char *argv[])
|
||||
// 清理缓冲区
|
||||
memset(segment_buffer, '\0', sizeof(segment_buffer));
|
||||
}
|
||||
|
||||
progress_print(line_count, total_line, true);
|
||||
printf("\n\n\n");
|
||||
}
|
||||
|
||||
// 清理数据列表
|
||||
{
|
||||
}
|
||||
|
||||
target_file_node = target_file_node->p_next;
|
141
Src/Tool_Functions.cpp
Normal file
141
Src/Tool_Functions.cpp
Normal file
@ -0,0 +1,141 @@
|
||||
#include "Tool_Functions.hpp"
|
||||
|
||||
extern "C"
|
||||
{
|
||||
#include "string.h"
|
||||
#include "ctype.h"
|
||||
}
|
||||
|
||||
// 行进到上一行起始位置
|
||||
size_t f_seek_pre_line_begin(FILE *file)
|
||||
{
|
||||
int count = 0;
|
||||
|
||||
// 本身就在文件起始位置
|
||||
if (ftell(file) == 0)
|
||||
return 0;
|
||||
// 本身在文件结尾
|
||||
if (fgetc(file) == EOF)
|
||||
{
|
||||
// 移动到之前
|
||||
do
|
||||
{
|
||||
fseek(file, -2, SEEK_CUR);
|
||||
count--;
|
||||
} while (ftell(file) != 0 && fgetc(file) != '\n');
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
// 其它情况
|
||||
|
||||
// 移动到上一行的结尾处(回到本行起始位置)
|
||||
while (ftell(file) != 0 && fgetc(file) != '\n')
|
||||
{
|
||||
fseek(file, -2, SEEK_CUR);
|
||||
count--;
|
||||
}
|
||||
|
||||
// 移动到上上一行的结尾处
|
||||
do
|
||||
{
|
||||
fseek(file, -2, SEEK_CUR);
|
||||
count--;
|
||||
} while (ftell(file) != 0 && fgetc(file) != '\n');
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
// 读取文件一行
|
||||
size_t f_getline(FILE *file, char *buffer, const size_t buffer_len)
|
||||
{
|
||||
if (buffer == nullptr || file == nullptr)
|
||||
return 0;
|
||||
|
||||
memset(buffer, '\0', buffer_len);
|
||||
|
||||
size_t count = 0;
|
||||
|
||||
// 循环读取
|
||||
while (true)
|
||||
{
|
||||
// 超长判定
|
||||
if (count + 1 == buffer_len)
|
||||
return buffer_len;
|
||||
|
||||
// 正常读取
|
||||
char ch = fgetc(file);
|
||||
|
||||
// 仅文件结尾时
|
||||
if (ch == EOF && count == 0)
|
||||
return 0;
|
||||
|
||||
// 成功换行
|
||||
if (ch == '\n')
|
||||
{
|
||||
buffer[count] = '\n';
|
||||
return count + 1;
|
||||
}
|
||||
|
||||
// 没有换行但是遇到了文件结尾
|
||||
if (ch == EOF)
|
||||
{
|
||||
buffer[count] = '\n';
|
||||
return count;
|
||||
}
|
||||
|
||||
// 其它情况下正常复制
|
||||
buffer[count] = ch;
|
||||
count++;
|
||||
}
|
||||
}
|
||||
|
||||
// 进度条打印
|
||||
void progress_print(size_t completed, size_t total, bool reflush)
|
||||
{
|
||||
|
||||
// 消除单行内容
|
||||
if (reflush)
|
||||
putchar('\r');
|
||||
else
|
||||
putchar('\n');
|
||||
|
||||
double p_percent = 1.0 * completed / total;
|
||||
|
||||
putchar('[');
|
||||
|
||||
// 输出完成部分填充
|
||||
size_t completed_count = (PROGRESS_LENGTH * p_percent) - 1;
|
||||
if (p_percent - (int)(p_percent) > 0.5)
|
||||
completed_count++;
|
||||
|
||||
for (int count = completed_count; count > 0; count--)
|
||||
putchar('=');
|
||||
putchar('>');
|
||||
|
||||
// 填充未完成部分
|
||||
for (int count = PROGRESS_LENGTH - (completed_count + 1); count > 0; count--)
|
||||
putchar(' ');
|
||||
putchar(']');
|
||||
|
||||
// 进度数显
|
||||
printf(" %d/%d (%%%.2lf)", completed, total, p_percent * 100);
|
||||
}
|
||||
|
||||
// 16进制字符串转十进制数值(8字节)
|
||||
uint64_t hex_to_decimal(const char *str)
|
||||
{
|
||||
uint64_t value = 0;
|
||||
|
||||
int len = strlen(str);
|
||||
// 循环读取
|
||||
for (int count = 0; count < len; count++)
|
||||
{
|
||||
value *= 16;
|
||||
if (str[count] >= '0' && str[count] <= '9')
|
||||
value += str[count] - '0';
|
||||
else
|
||||
value += toupper(str[count]) - 'A' + 10;
|
||||
}
|
||||
return value;
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user