/// <summary> /// 创建结构体 /// </summary> /// <typeparam name="TEntity"></typeparam> /// <param name="entity"></param> /// <param name="address"></param> /// <param name="canPostfix"></param> /// <returns></returns> public static Struct Create <TEntity>(TEntity entity, UInt32 address, Boolean canPostfix) where TEntity : EntityBase <TEntity>, new() { Type type = typeof(TEntity); // 类名作为结构体名字 String name = type.Name; // 检查是否已存在 //UInt32 id = Struct.GetStructID(name); //if (id != Bytes.BadAddress) //{ // KernelWin.WriteLine("结构体{0}(ID={1:X}h)已存在!", name, id); // return Struct.FindStructByID(id); //} Struct st = Struct.FindStructByName(name); //if (st != null) //{ // KernelWin.WriteLine("结构体{0}(ID={1:X}h)已存在!", name, st.ID); // return st; //} Int32 n = 0; String name2 = name; while (st == null) { st = Struct.Create(name2, Bytes.BadAddress, false); n++; if (st == null) { if (n > 10 || !canPostfix) { throw new Exception("创建结构体失败!"); } name2 = name + "_" + n; } } Dictionary <String, DataFieldItem> dic = DataFieldItem.GetFields(type); foreach (DataFieldItem item in dic.Values) { name = item.Property.Name; DataType dt; UInt32 size = 0; if (item.Attribute.RefType == null) { #region 普通成员 if (item.Property.PropertyType == typeof(String)) { dt = DataType.ASCI; if (!String.IsNullOrEmpty(item.Attribute.SizeField)) { size = Convert.ToUInt32(entity[item.Attribute.SizeField]); } if (size <= 0) { size = (UInt32)item.Attribute.Size; } } else if (item.Property.PropertyType == typeof(Byte[])) { // 字节数组也可以当作字符串一样处理 dt = DataType.ASCI; if (!String.IsNullOrEmpty(item.Attribute.SizeField)) { size = Convert.ToUInt32(entity[item.Attribute.SizeField]); } if (size <= 0) { size = (UInt32)item.Attribute.Size; } } else if (item.Property.PropertyType == typeof(Byte)) { dt = DataType.BYTE; size = 1; } else if (item.Property.PropertyType == typeof(Int16)) { dt = DataType.WORD; size = 2; } else if (item.Property.PropertyType == typeof(Int32)) { dt = DataType.DWRD; size = 4; } else { throw new Exception("不支持的类型:" + type.Name); } //KernelWin.WriteLine("创建普通成员:{0} {1} {2} ", name, dt, size); st.Add(name, dt, size); #endregion } else { #region 引用成员 if (item.Property.PropertyType == typeof(Int16)) { dt = DataType.WORD | DataType.F0OFF; size = 2; } else if (item.Property.PropertyType == typeof(Int32)) { dt = DataType.DWRD | DataType.F0OFF; size = 4; } else { throw new Exception("不支持的类型:" + type.Name); } UInt32 addr = 0; switch (item.Attribute.RefKind) { case RefKinds.Virtual: addr = 0; break; case RefKinds.Relative: addr = address; break; case RefKinds.Auto: // 先直接取地址 addr = Convert.ToUInt32(item.Property.GetValue(entity, null)); // 如果小于基址,可能是相对地址 if (addr < entity.Info.ImageBase && addr > 0) { addr = address; } else { addr = 0; } break; case RefKinds.Absolute: throw new Exception("不支持的类型:" + item.Attribute.RefKind); } //KernelWin.WriteLine("创建引用成员:{0} {1} 0x{2:X} {3}", name, dt, addr, size); st.Add(name, Bytes.BadAddress, dt, addr, size); #endregion } } return(st); }