feat(lexer, preprocessor): replace cstring conversion with copy and refactor macro expansion
- Replace `scc_cstring_from_cstr(scc_cstring_as_cstr(...))` with `scc_cstring_copy()` in lexer to fix memory leaks - Extract macro expansion logic into separate `expand_macro.c` file - Remove `expand_stack` parameter from `scc_pp_expand_macro()` function - Add new parsing functions for macro replacement lists and arguments - Add string utility functions for whitespace trimming and string joining - Update memory stream documentation for clarity
This commit is contained in:
@@ -1,12 +1,12 @@
|
||||
/**
|
||||
* @file hashmap.h
|
||||
* @file hashtable.h
|
||||
* @brief 开放寻址法哈希表实现
|
||||
*
|
||||
* 提供基于向量容器的哈希表实现,支持动态扩容和墓碑机制
|
||||
*/
|
||||
|
||||
#ifndef __SCC_HASHMAP_H__
|
||||
#define __SCC_HASHMAP_H__
|
||||
#ifndef __SCC_HASHTABLE_H__
|
||||
#define __SCC_HASHTABLE_H__
|
||||
|
||||
#include <libcore.h>
|
||||
|
||||
@@ -121,4 +121,4 @@ typedef int (*scc_hashtable_iter_fn)(const void *key, void *value,
|
||||
void scc_hashtable_foreach(scc_hashtable_t *ht, scc_hashtable_iter_fn iter_func,
|
||||
void *context);
|
||||
|
||||
#endif /* __SCC_HASHMAP_H__ */
|
||||
#endif /* __SCC_HASHTABLE_H__ */
|
||||
@@ -1,9 +1,9 @@
|
||||
#ifndef __SMCC_UTILS_H__
|
||||
#define __SMCC_UTILS_H__
|
||||
|
||||
#include "hashmap.h"
|
||||
#include "hashtable.h"
|
||||
#include "kllist.h"
|
||||
#include "strpool.h"
|
||||
#include <libcore.h>
|
||||
|
||||
#endif // __SMCC_UTILS_H__
|
||||
#endif /* __SMCC_UTILS_H__ */
|
||||
|
||||
@@ -8,7 +8,7 @@
|
||||
#ifndef __SCC_STRPOOL_H__
|
||||
#define __SCC_STRPOOL_H__
|
||||
|
||||
#include "hashmap.h"
|
||||
#include "hashtable.h"
|
||||
#include <libcore.h>
|
||||
|
||||
/**
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
#include <hashmap.h>
|
||||
#include <hashtable.h>
|
||||
|
||||
#ifndef SCC_INIT_HASHMAP_SIZE
|
||||
#define SCC_INIT_HASHMAP_SIZE (32)
|
||||
@@ -1,112 +0,0 @@
|
||||
# vector_gdb.py
|
||||
import gdb # type: ignore
|
||||
from gdb.printing import PrettyPrinter # type: ignore
|
||||
|
||||
class VectorPrinter:
|
||||
"""兼容新旧注册方式的最终方案"""
|
||||
|
||||
def __init__(self, val: gdb.Value):
|
||||
self.val:gdb.Value = val
|
||||
|
||||
def check_type(self) -> bool:
|
||||
"""类型检查(兼容匿名结构体)"""
|
||||
try:
|
||||
if self.val.type.code != gdb.TYPE_CODE_STRUCT:
|
||||
return False
|
||||
fields = self.val.type.fields()
|
||||
if not fields:
|
||||
return False
|
||||
exp = ['size', 'cap', 'data']
|
||||
for t in fields:
|
||||
if t.name in exp:
|
||||
exp.remove(t.name)
|
||||
else:
|
||||
return False
|
||||
return True
|
||||
except gdb.error:
|
||||
return False
|
||||
|
||||
def to_string(self):
|
||||
if not self.check_type():
|
||||
return "Not a vector"
|
||||
|
||||
return "vector({} size={}, cap={})".format(
|
||||
self.val.address,
|
||||
self.val['size'],
|
||||
self.val['cap'],
|
||||
)
|
||||
|
||||
def display_hint(self):
|
||||
return 'array'
|
||||
|
||||
def children(self):
|
||||
"""生成数组元素(关键改进点)"""
|
||||
if not self.check_type():
|
||||
return []
|
||||
|
||||
size = int(self.val['size'])
|
||||
cap = int(self.val['cap'])
|
||||
data_ptr = self.val['data']
|
||||
|
||||
if cap == 0 or data_ptr == 0:
|
||||
return []
|
||||
|
||||
# 使用 GDB 内置数组转换
|
||||
array = data_ptr.dereference()
|
||||
array = array.cast(data_ptr.type.target().array(cap - 1))
|
||||
|
||||
for i in range(size):
|
||||
# state = "<used>" if i < size else "<unused>"
|
||||
try:
|
||||
value = array[i]
|
||||
yield (f"[{i}] {value.type} {value.address}", value)
|
||||
except gdb.MemoryError:
|
||||
yield (f"[{i}]", "<invalid>")
|
||||
|
||||
# 注册方式一:传统append方法(您之前有效的方式)self
|
||||
def append_printer():
|
||||
gdb.pretty_printers.append(
|
||||
lambda val: VectorPrinter(val) if VectorPrinter(val).check_type() else None
|
||||
)
|
||||
|
||||
# 注册方式二:新版注册方法(备用方案)
|
||||
def register_new_printer():
|
||||
class VectorPrinterLocator(PrettyPrinter):
|
||||
def __init__(self):
|
||||
super().__init__("vector_printer")
|
||||
|
||||
def __call__(self, val):
|
||||
ret = VectorPrinter(val).check_type()
|
||||
print(f"ret {ret}, type {val.type}, {[(i.name, i.type) for i in val.type.fields()]}")
|
||||
return None
|
||||
|
||||
gdb.printing.register_pretty_printer(
|
||||
gdb.current_objfile(),
|
||||
VectorPrinterLocator()
|
||||
)
|
||||
|
||||
# 双重注册保证兼容性
|
||||
append_printer() # 保留您原来有效的方式
|
||||
# register_new_printer() # 添加新版注册
|
||||
|
||||
class VectorInfoCommand(gdb.Command):
|
||||
"""保持原有命令不变"""
|
||||
def __init__(self):
|
||||
super().__init__("vector_info", gdb.COMMAND_USER)
|
||||
|
||||
def invoke(self, argument, from_tty):
|
||||
val = gdb.parse_and_eval(argument)
|
||||
printer = VectorPrinter(val)
|
||||
|
||||
if not printer.check_type():
|
||||
print("Invalid vector")
|
||||
return
|
||||
|
||||
print("=== Vector Details ===")
|
||||
print("Size:", val['size'])
|
||||
print("Capacity:", val['cap'])
|
||||
print("Elements:")
|
||||
for name, value in printer.children():
|
||||
print(f" {name}: {value}")
|
||||
|
||||
VectorInfoCommand()
|
||||
Reference in New Issue
Block a user