private void OnNetworkMessage(IntPtr dataPtr, ushort opCode, uint sourceActorId, uint targetActorId, NetworkMessageDirection direction) { if (direction != NetworkMessageDirection.ZoneDown) { return; } if (!this.dalamud.Data.IsDataReady) { return; } if (opCode == this.dalamud.Data.ServerOpCodes["CfNotifyPop"]) { var data = new byte[64]; Marshal.Copy(dataPtr, data, 0, 64); var notifyType = data[0]; var contentFinderConditionId = BitConverter.ToUInt16(data, 0x14); if (notifyType != 3) { return; } var contentFinderCondition = this.dalamud.Data.GetExcelSheet <ContentFinderCondition>().GetRow(contentFinderConditionId); if (contentFinderCondition == null) { Log.Error("CFC key {0} not in lumina data.", contentFinderConditionId); return; } var cfcName = contentFinderCondition.Name.ToString(); if (string.IsNullOrEmpty(contentFinderCondition.Name)) { cfcName = "Duty Roulette"; contentFinderCondition.Image = 112324; } if (this.dalamud.Configuration.DutyFinderTaskbarFlash && !NativeFunctions.ApplicationIsActivated()) { var flashInfo = new NativeFunctions.FLASHWINFO { cbSize = (uint)Marshal.SizeOf <NativeFunctions.FLASHWINFO>(), uCount = uint.MaxValue, dwTimeout = 0, dwFlags = NativeFunctions.FlashWindow.FLASHW_ALL | NativeFunctions.FlashWindow.FLASHW_TIMERNOFG, hwnd = Process.GetCurrentProcess().MainWindowHandle }; NativeFunctions.FlashWindowEx(ref flashInfo); } Task.Run(() => { if (this.dalamud.Configuration.DutyFinderChatMessage) { this.dalamud.Framework.Gui.Chat.Print("Duty pop: " + cfcName); } CfPop?.Invoke(this, contentFinderCondition); }); return; } if (!this.optOutMbUploads) { if (opCode == this.dalamud.Data.ServerOpCodes["MarketBoardItemRequestStart"]) { var catalogId = (uint)Marshal.ReadInt32(dataPtr); var amount = Marshal.ReadByte(dataPtr + 0xB); this.marketBoardRequests.Add(new MarketBoardItemRequest { CatalogId = catalogId, AmountToArrive = amount, Listings = new List <MarketBoardCurrentOfferings.MarketBoardItemListing>(), History = new List <MarketBoardHistory.MarketBoardHistoryListing>() }); Log.Verbose($"NEW MB REQUEST START: item#{catalogId} amount#{amount}"); return; } if (opCode == this.dalamud.Data.ServerOpCodes["MarketBoardOfferings"]) { var listing = MarketBoardCurrentOfferings.Read(dataPtr); var request = this.marketBoardRequests.LastOrDefault( r => r.CatalogId == listing.ItemListings[0].CatalogId && !r.IsDone); if (request == null) { Log.Error( $"Market Board data arrived without a corresponding request: item#{listing.ItemListings[0].CatalogId}"); return; } if (request.Listings.Count + listing.ItemListings.Count > request.AmountToArrive) { Log.Error( $"Too many Market Board listings received for request: {request.Listings.Count + listing.ItemListings.Count} > {request.AmountToArrive} item#{listing.ItemListings[0].CatalogId}"); return; } if (request.ListingsRequestId != -1 && request.ListingsRequestId != listing.RequestId) { Log.Error( $"Non-matching RequestIds for Market Board data request: {request.ListingsRequestId}, {listing.RequestId}"); return; } if (request.ListingsRequestId == -1 && request.Listings.Count > 0) { Log.Error( $"Market Board data request sequence break: {request.ListingsRequestId}, {request.Listings.Count}"); return; } if (request.ListingsRequestId == -1) { request.ListingsRequestId = listing.RequestId; Log.Verbose($"First Market Board packet in sequence: {listing.RequestId}"); } request.Listings.AddRange(listing.ItemListings); Log.Verbose("Added {0} ItemListings to request#{1}, now {2}/{3}, item#{4}", listing.ItemListings.Count, request.ListingsRequestId, request.Listings.Count, request.AmountToArrive, request.CatalogId); if (request.IsDone) { Log.Verbose("Market Board request finished, starting upload: request#{0} item#{1} amount#{2}", request.ListingsRequestId, request.CatalogId, request.AmountToArrive); try { Task.Run(() => this.uploader.Upload(request)); } catch (Exception ex) { Log.Error(ex, "Market Board data upload failed."); } } return; } if (opCode == this.dalamud.Data.ServerOpCodes["MarketBoardHistory"]) { var listing = MarketBoardHistory.Read(dataPtr); var request = this.marketBoardRequests.LastOrDefault(r => r.CatalogId == listing.CatalogId); if (request == null) { Log.Error( $"Market Board data arrived without a corresponding request: item#{listing.CatalogId}"); return; } if (request.ListingsRequestId != -1) { Log.Error( $"Market Board data history sequence break: {request.ListingsRequestId}, {request.Listings.Count}"); return; } request.History.AddRange(listing.HistoryListings); Log.Verbose("Added history for item#{0}", listing.CatalogId); if (request.AmountToArrive == 0) { Log.Verbose("Request had 0 amount, uploading now"); try { Task.Run(() => this.uploader.Upload(request)); } catch (Exception ex) { Log.Error(ex, "Market Board data upload failed."); } } } if (opCode == this.dalamud.Data.ServerOpCodes["MarketTaxRates"]) { var category = (uint)Marshal.ReadInt32(dataPtr); // Result dialog packet does not contain market tax rates if (category != 720905) { return; } var taxes = MarketTaxRates.Read(dataPtr); Log.Verbose("MarketTaxRates: limsa#{0} grid#{1} uldah#{2} ish#{3} kugane#{4} cr#{5}", taxes.LimsaLominsaTax, taxes.GridaniaTax, taxes.UldahTax, taxes.IshgardTax, taxes.KuganeTax, taxes.CrystariumTax); try { Task.Run(() => this.uploader.UploadTax(taxes)); } catch (Exception ex) { Log.Error(ex, "Market Board data upload failed."); } } } }
public static void RightClickToTP(GameContext Context) { byte s = 0; NativeFunctions.ReadProcessMemory(Context.HContext.Handle, Context.HContext.MainAddressHelper.GetFunctionAddress("Terraria.Main", "DoUpdate"), ref s, 1, 0); if (s == 0xE9) //已经被修改,不能再hook { return; } var ass = AssemblySnippet.FromCode( new AssemblyCode[] { Instruction.Create("pushad"), Instruction.Create($"cmp byte ptr [{Context.MapFullScreen_Address}],0"), Instruction.Create("je _rwualfna"), Instruction.Create($"cmp byte ptr [{Context.MouseRight_Address}],0"), Instruction.Create("je _rwualfna"), Instruction.Create($"cmp byte ptr [{Context.MouseRightRelease_Address}],0"), Instruction.Create("je _rwualfna"), AssemblySnippet.FromCode( new AssemblyCode[] { Instruction.Create($"mov byte ptr [{Context.MapFullScreen_Address}],0"), Instruction.Create($"mov byte ptr [{Context.MouseRightRelease_Address}],0"), AssemblySnippet.FromClrCall( Context.HContext.MainAddressHelper.GetFunctionAddress("Terraria.Main", "get_LocalPlayer"), null, false), Instruction.Create("mov ebx,eax"), Instruction.Create("push eax"), Instruction.Create("mov dword ptr [esp],2"), Instruction.Create($"fild dword ptr [{Context.ScreenWidth_Address}]"), Instruction.Create("fild dword ptr [esp]"), Instruction.Create("fdivp"), Instruction.Create($"fild dword ptr [{Context.MouseX_Address}]"), Instruction.Create("fsubp"), Instruction.Create($"fld dword ptr [{Context.MapFullScreenScale_Address}]"), Instruction.Create("fdivp"), Instruction.Create($"fld dword ptr [{Context.MapFullscreenPos_Address + 4}]"), Instruction.Create("fsubrp"), Instruction.Create("mov dword ptr [esp],16"), Instruction.Create("fild dword ptr [esp]"), Instruction.Create("fmulp"), Instruction.Create($"fstp dword ptr [ebx+{Entity.OFFSET_Position}]"), Instruction.Create("mov dword ptr [esp],2"), Instruction.Create($"fild dword ptr [{Context.ScreenHeight_Address}]"), Instruction.Create("fild dword ptr [esp]"), Instruction.Create("fdivp"), Instruction.Create($"fild dword ptr [{Context.MouseY_Address}]"), Instruction.Create("fsubp"), Instruction.Create($"fld dword ptr [{Context.MapFullScreenScale_Address}]"), Instruction.Create("fdivp"), Instruction.Create($"fld dword ptr [{Context.MapFullscreenPos_Address + 8}]"), Instruction.Create("fsubrp"), Instruction.Create("mov dword ptr [esp],16"), Instruction.Create("fild dword ptr [esp]"), Instruction.Create("fmulp"), Instruction.Create($"fstp dword ptr [ebx+{Entity.OFFSET_Position + 0x4}]"), Instruction.Create("pop eax"), }), Instruction.Create("_rwualfna:"), Instruction.Create("popad") }); InlineHook.Inject(Context.HContext, ass, Context.HContext.MainAddressHelper.GetFunctionAddress("Terraria.Main", "DoUpdate") + 5, false); }
public Vector3 ToScreenCoords() { var retval = NativeFunctions.GetScreenCoords(this.ToSVector()); return(new Vector3(retval)); }
private void OnNetworkMessage(IntPtr dataPtr, ushort opCode, uint sourceActorId, uint targetActorId, NetworkMessageDirection direction) { if (direction != NetworkMessageDirection.ZoneDown) { return; } if (!this.dalamud.Data.IsDataReady) { return; } if (opCode == this.dalamud.Data.ServerOpCodes["CfNotifyPop"]) { var data = new byte[64]; Marshal.Copy(dataPtr, data, 0, 64); var notifyType = data[0]; var contentFinderConditionId = BitConverter.ToUInt16(data, 0x14); if (notifyType != 3) { return; } var contentFinderCondition = this.dalamud.Data.GetExcelSheet <ContentFinderCondition>().GetRow(contentFinderConditionId); if (contentFinderCondition == null) { Log.Error("CFC key {0} not in lumina data.", contentFinderConditionId); return; } if (string.IsNullOrEmpty(contentFinderCondition.Name)) { contentFinderCondition.Name = "Duty Roulette"; contentFinderCondition.Image = 112324; } if (this.dalamud.Configuration.DutyFinderTaskbarFlash && !NativeFunctions.ApplicationIsActivated()) { var flashInfo = new NativeFunctions.FLASHWINFO { cbSize = (uint)Marshal.SizeOf <NativeFunctions.FLASHWINFO>(), uCount = uint.MaxValue, dwTimeout = 0, dwFlags = NativeFunctions.FlashWindow.FLASHW_ALL | NativeFunctions.FlashWindow.FLASHW_TIMERNOFG, hwnd = Process.GetCurrentProcess().MainWindowHandle }; NativeFunctions.FlashWindowEx(ref flashInfo); } Task.Run(async() => { this.dalamud.Framework.Gui.Chat.Print("Duty pop: " + contentFinderCondition.Name); await this.ProcessCfPop?.Invoke(contentFinderCondition); }); return; } if (opCode == this.dalamud.Data.ServerOpCodes["CfPreferredRole"]) { if (this.dalamud.Configuration.PreferredRoleReminders == null) { return; } var data = new byte[64]; Marshal.Copy(dataPtr, data, 0, 32); if (this.lastPreferredRole == null) { this.lastPreferredRole = data; return; } Task.Run(async() => { for (var rouletteIndex = 1; rouletteIndex < 11; rouletteIndex++) { var currentRoleKey = data[rouletteIndex]; var prevRoleKey = this.lastPreferredRole[rouletteIndex]; Log.Verbose("CfPreferredRole: {0} - {1} => {2}", rouletteIndex, prevRoleKey, currentRoleKey); if (currentRoleKey != prevRoleKey) { var rouletteName = rouletteIndex switch { 1 => "Duty Roulette: Leveling", 2 => "Duty Roulette: Level 50/60/70 Dungeons", 3 => "Duty Roulette: Main Scenario", 4 => "Duty Roulette: Guildhests", 5 => "Duty Roulette: Expert", 6 => "Duty Roulette: Trials", 8 => "Duty Roulette: Mentor", 9 => "Duty Roulette: Alliance Raids", 10 => "Duty Roulette: Normal Raids", _ => "Unknown ContentRoulette" }; var prevRoleName = RoleKeyToPreferredRole(prevRoleKey); var currentRoleName = RoleKeyToPreferredRole(currentRoleKey); if (!this.dalamud.Configuration.PreferredRoleReminders.TryGetValue(rouletteIndex, out var roleToCheck)) { return; } if (roleToCheck == DalamudConfiguration.PreferredRole.All || currentRoleName != roleToCheck) { return; } this.dalamud.Framework.Gui.Chat.Print($"Roulette bonus for {rouletteName} changed: {prevRoleName} => {currentRoleName}"); if (this.dalamud.BotManager.IsConnected) { await this.dalamud.BotManager.ProcessCfPreferredRoleChange(rouletteName, prevRoleName.ToString(), currentRoleName.ToString()); } } } this.lastPreferredRole = data; }); return; } if (!this.optOutMbUploads) { if (opCode == this.dalamud.Data.ServerOpCodes["MarketBoardItemRequestStart"]) { var catalogId = (uint)Marshal.ReadInt32(dataPtr); var amount = Marshal.ReadByte(dataPtr + 0xB); this.marketBoardRequests.Add(new MarketBoardItemRequest { CatalogId = catalogId, AmountToArrive = amount, Listings = new List <MarketBoardCurrentOfferings.MarketBoardItemListing>(), History = new List <MarketBoardHistory.MarketBoardHistoryListing>() }); Log.Verbose($"NEW MB REQUEST START: item#{catalogId} amount#{amount}"); return; } if (opCode == this.dalamud.Data.ServerOpCodes["MarketBoardOfferings"]) { var listing = MarketBoardCurrentOfferings.Read(dataPtr); var request = this.marketBoardRequests.LastOrDefault( r => r.CatalogId == listing.ItemListings[0].CatalogId && !r.IsDone); if (request == null) { Log.Error( $"Market Board data arrived without a corresponding request: item#{listing.ItemListings[0].CatalogId}"); return; } if (request.Listings.Count + listing.ItemListings.Count > request.AmountToArrive) { Log.Error( $"Too many Market Board listings received for request: {request.Listings.Count + listing.ItemListings.Count} > {request.AmountToArrive} item#{listing.ItemListings[0].CatalogId}"); return; } if (request.ListingsRequestId != -1 && request.ListingsRequestId != listing.RequestId) { Log.Error( $"Non-matching RequestIds for Market Board data request: {request.ListingsRequestId}, {listing.RequestId}"); return; } if (request.ListingsRequestId == -1 && request.Listings.Count > 0) { Log.Error( $"Market Board data request sequence break: {request.ListingsRequestId}, {request.Listings.Count}"); return; } if (request.ListingsRequestId == -1) { request.ListingsRequestId = listing.RequestId; Log.Verbose($"First Market Board packet in sequence: {listing.RequestId}"); } request.Listings.AddRange(listing.ItemListings); Log.Verbose("Added {0} ItemListings to request#{1}, now {2}/{3}, item#{4}", listing.ItemListings.Count, request.ListingsRequestId, request.Listings.Count, request.AmountToArrive, request.CatalogId); if (request.IsDone) { Log.Verbose("Market Board request finished, starting upload: request#{0} item#{1} amount#{2}", request.ListingsRequestId, request.CatalogId, request.AmountToArrive); try { Task.Run(() => this.uploader.Upload(request)); } catch (Exception ex) { Log.Error(ex, "Market Board data upload failed."); } } return; } if (opCode == this.dalamud.Data.ServerOpCodes["MarketBoardHistory"]) { var listing = MarketBoardHistory.Read(dataPtr); var request = this.marketBoardRequests.LastOrDefault(r => r.CatalogId == listing.CatalogId); if (request == null) { Log.Error( $"Market Board data arrived without a corresponding request: item#{listing.CatalogId}"); return; } if (request.ListingsRequestId != -1) { Log.Error( $"Market Board data history sequence break: {request.ListingsRequestId}, {request.Listings.Count}"); return; } request.History.AddRange(listing.HistoryListings); Log.Verbose("Added history for item#{0}", listing.CatalogId); } if (opCode == this.dalamud.Data.ServerOpCodes["MarketTaxRates"]) { var taxes = MarketTaxRates.Read(dataPtr); Log.Verbose("MarketTaxRates: limsa#{0} grid#{1} uldah#{2} ish#{3} kugane#{4} cr#{5}", taxes.LimsaLominsaTax, taxes.GridaniaTax, taxes.UldahTax, taxes.IshgardTax, taxes.KuganeTax, taxes.CrystariumTax); try { Task.Run(() => this.uploader.UploadTax(taxes)); } catch (Exception ex) { Log.Error(ex, "Market Board data upload failed."); } } } }
public void InterfaceInArrays() { Interface[] results = new Interface[4]; NativeFunctions.GetInterfacesWithRelation(results); NativeFunctions.InInterfaceArray(results); }
/// <summary> /// 凡是没有标明Pointer的,获取的均为基址,而非指向该地址的指针 /// 基础数据类型没有基址,获得的是地址,而非基址 /// </summary> /// <param name="pid">游戏的进程ID</param> private GameContext(int pid) { HContext = Context.Create(pid); ArrayHeadLength = HContext.ArrayHeadLength; InitalizeOffsets(); int v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "player"); Player_Array_Pointer = v; NativeFunctions.ReadProcessMemory(HContext.Handle, v, ref v, 4, 0); Player_Array_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "myPlayer"); My_Player_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "npc"); NPC_Array_Pointer = v; NativeFunctions.ReadProcessMemory(HContext.Handle, v, ref v, 4, 0); NPC_Array_Address = v; //下面两个取的是值,而非地址 v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "maxTilesX"); NativeFunctions.ReadProcessMemory(HContext.Handle, v, ref v, 4, 0); MaxTilesX = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "maxTilesY"); NativeFunctions.ReadProcessMemory(HContext.Handle, v, ref v, 4, 0); MaxTilesY = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "Map"); Main_Map_Pointer = v; NativeFunctions.ReadProcessMemory(HContext.Handle, v, ref v, 4, 0); Main_Map_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "refreshMap"); Main_RefreshMap_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "mapFullscreen"); MapFullScreen_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "mouseRight"); MouseRight_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "mouseRightRelease"); MouseRightRelease_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "screenWidth"); ScreenWidth_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "screenHeight"); ScreenHeight_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "mapFullscreenPos"); MapFullscreenPos_Pointer = v; NativeFunctions.ReadProcessMemory(HContext.Handle, v, ref v, 4, 0); MapFullscreenPos_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "mouseX"); MouseX_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "mouseY"); MouseY_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "mapFullscreenScale"); MapFullScreenScale_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "tile"); Tile_Pointer = v; NativeFunctions.ReadProcessMemory(HContext.Handle, v, ref v, 4, 0); Tile_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "netMode"); NetMode_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Player", "tileTargetX"); TileTargetX_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Player", "tileTargetY"); TileTargetY_Address = v; v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "debuff"); Debuff_Pointer = v; NativeFunctions.ReadProcessMemory(HContext.Handle, v, ref v, 4, 0); Debuff_Address = v; //这里使用了自适应的数组头部长度,如果无效将会被修改 int bbbb = 0; NativeFunctions.ReadProcessMemory(HContext.Handle, v + HContext.ArrayHeadLength - 4, ref bbbb, 4, 0); Debuff = new int[bbbb]; for (int i = 0; i < bbbb; i++) { NativeFunctions.ReadProcessMemory(HContext.Handle, Debuff_Address + HContext.ArrayHeadLength + i, ref Debuff[i], 1, 0); } v = HContext.MainAddressHelper.GetStaticFieldAddress("Terraria.Main", "ActiveWorldFileData"); ActiveWorldFileData_Pointer = v; NativeFunctions.ReadProcessMemory(HContext.Handle, v, ref v, 4, 0); ActiveWorldFileData_Address = v; }
public void OptionalStructArrayOut() { NativeFunctions.StructArrayOut(new StructWithMarshal(), null); }
internal void Render(CommandBuffer cmd, Camera camera, RenderTargetIdentifier renderTarget, Material material) { //cmd.ClearRenderTarget(false, true, Color.green); foreach (var lineEffect in camera.GetComponents <PencilLineEffect>()) { if (lineEffect.PencilRenderer != null && lineEffect.PencilRenderer.Texture != null && lineEffect.isPostProsessingEnabled) { // テクスチャ更新設定 if (lineEffect.isRendering == true) { #if UNITY_2018_3_OR_NEWER var callback = NativeFunctions.GetTextureUpdateCallbackV2(); #else var callback = NativeFunctions.GetTextureUpdateCallback(); #endif if (callback == IntPtr.Zero) { continue; } // ハンドルを取得し、ネイティブで確保したバッファが意図せず解放されないようにする // ハンドルはTextureUpdateCallback()のEndで自動的に解除される var textureUpdateHandle = lineEffect.PencilRenderer.RequestTextureUpdate(0); if (textureUpdateHandle == 0xFFFFFFFF) { // PencilLinePostProcessRenderer.Render()の呼び出しがlineEffect.OnPreRender()よりも早いケースが稀にあり、 // PostProcessing_RenderingEventモードのときに適切なライン描画が行われない場合がある continue; } #if UNITY_2018_3_OR_NEWER cmd.IssuePluginCustomTextureUpdateV2(callback, lineEffect.PencilRenderer.Texture, textureUpdateHandle); #else cmd.IssuePluginCustomTextureUpdate(callback, lineEffect.PencilRenderer.Texture, textureUpdateHandle); #endif // レンダーエレメント画像出力用のテクスチャ更新 for (int renderElementIndex = 0; true; renderElementIndex++) { var renderElementTexture = lineEffect.PencilRenderer.GetRenderElementTexture(renderElementIndex); var renderElementTargetTexture = lineEffect.PencilRenderer.GetRenderElementTargetTexture(renderElementIndex); if (renderElementTexture == null || renderElementTargetTexture == null) { break; } textureUpdateHandle = lineEffect.PencilRenderer.RequestTextureUpdate(1 + renderElementIndex); if (textureUpdateHandle == 0xFFFFFFFF) { break; } #if UNITY_2018_3_OR_NEWER cmd.IssuePluginCustomTextureUpdateV2(callback, renderElementTexture, textureUpdateHandle); #else cmd.IssuePluginCustomTextureUpdate(callback, renderElementTexture, textureUpdateHandle); #endif cmd.Blit(renderElementTexture, renderElementTargetTexture); } } // 描画設定 cmd.SetGlobalFloat("_Alpha", alpha.value); cmd.Blit(lineEffect.PencilRenderer.Texture, renderTarget, material); } } }
public void PointerSize() { var value = new PointerSize(20); Assert.Equal(new PointerSize(20), NativeFunctions.PassThroughPointerSize(value)); }
public void InterfaceOutArraysOptional() { int num = 3; NativeFunctions.GetInterfacesOptional(num, null); }
public void ParamsArray() { Assert.Equal(10, NativeFunctions.Product(1, new SimpleStruct { I = 10 })); }
public void StringReturnTest() { Assert.Equal("Functions", NativeFunctions.GetName()); }
public void BoolToIntTest() { Assert.True(NativeFunctions.BoolToIntTest(true)); Assert.False(NativeFunctions.BoolToIntTest(false)); }
public void NullableParameterTest() { Assert.Equal(2, NativeFunctions.Add(2, null)); Assert.Equal(2, NativeFunctions.Add(1, 1)); }
public void WrappedStructAsClass() { Assert.Equal(1, NativeFunctions.GetWrapper().Wrapped.I); }
/// <summary> /// 这个函数被lock了,无法被多个线程同时调用,预防了一些错误 /// </summary> /// <param name="Context"></param> /// <param name="snippet"></param> /// <param name="targetAddr"></param> /// <param name="once"></param> /// <param name="execRaw"></param> /// <param name="codeSize"></param> /// <returns></returns> public static Tuple <int, int, int, byte[]> Inject(Context Context, AssemblySnippet snippet, int targetAddr, bool once, bool execRaw = true, int codeSize = 1024) { lock (thisLock) { int codeAddr = NativeFunctions.VirtualAllocEx(Context.Handle, 0, codeSize, NativeFunctions.AllocationType.Commit, NativeFunctions.MemoryProtection.ExecuteReadWrite); int compAddr = NativeFunctions.VirtualAllocEx(Context.Handle, 0, codeSize, NativeFunctions.AllocationType.Commit, NativeFunctions.MemoryProtection.ExecuteReadWrite); int flagAddr = 0; AssemblySnippet a = AssemblySnippet.FromEmpty(); a.Content.Add(Instruction.Create("__$$__:")); //very begin a.Content.Add(Instruction.Create("mov dword ptr [" + compAddr + "],1")); if (once) { flagAddr = NativeFunctions.VirtualAllocEx(Context.Handle, 0, codeSize, NativeFunctions.AllocationType.Commit, NativeFunctions.MemoryProtection.ExecuteReadWrite); NativeFunctions.WriteProcessMemory(Context.Handle, flagAddr, ref once, 4, 0); a.Content.Add(Instruction.Create("cmp dword ptr [" + flagAddr + "],0")); a.Content.Add(Instruction.Create("jle jalkjflakjl")); } a.Content.Add(snippet); if (once) { a.Content.Add(Instruction.Create("dec dword ptr [" + flagAddr + "]")); a.Content.Add(Instruction.Create("jalkjflakjl:")); } byte[] code = new byte[32]; NativeFunctions.ReadProcessMemory(Context.Handle, targetAddr, code, code.Length, 0); byte[] headBytes = GetHeadBytes(code); NativeFunctions.WriteProcessMemory(Context.Handle, codeAddr, ref flagAddr, 4, 0); NativeFunctions.WriteProcessMemory(Context.Handle, codeAddr + 4, ref compAddr, 4, 0); int addr = codeAddr + CodeOffset; byte[] snippetBytes = a.GetByteCode(addr); NativeFunctions.WriteProcessMemory(Context.Handle, addr, snippetBytes, snippetBytes.Length, 0); addr += snippetBytes.Length; if (execRaw) { NativeFunctions.WriteProcessMemory(Context.Handle, addr, headBytes, headBytes.Length, 0); addr += headBytes.Length; } byte[] compBytes = Assembler.Assemble("mov dword ptr [" + compAddr + "],0", addr); NativeFunctions.WriteProcessMemory(Context.Handle, addr, compBytes, compBytes.Length, 0); addr += compBytes.Length; byte[] jmpBackBytes = Assembler.Assemble("jmp " + (targetAddr + headBytes.Length), addr); NativeFunctions.WriteProcessMemory(Context.Handle, addr, jmpBackBytes, jmpBackBytes.Length, 0); addr += jmpBackBytes.Length; byte[] jmpToBytesRaw = Assembler.Assemble("jmp " + (codeAddr + CodeOffset), targetAddr); byte[] jmpToBytes = new byte[headBytes.Length]; for (int i = 0; i < 5; i++) { jmpToBytes[i] = jmpToBytesRaw[i]; } for (int i = 5; i < headBytes.Length; i++) { jmpToBytes[i] = 0x90; //nop } //Console.WriteLine(codeAddr.ToString("X8")); //Console.ReadKey(); NativeFunctions.WriteProcessMemory(Context.Handle, targetAddr, jmpToBytes, jmpToBytes.Length, 0); return(new Tuple <int, int, int, byte[]>(codeAddr, flagAddr, compAddr, headBytes)); } }
public void EnumArrayTest() { var test = new [] { MyEnum.TestValue, MyEnum.TestValue }; Assert.Equal(MyEnum.TestValue, NativeFunctions.FirstEnumElement(test)); }
public InterfaceManager(Dalamud dalamud, SigScanner scanner) { this.dalamud = dalamud; try { var sigResolver = new SwapChainSigResolver(); sigResolver.Setup(scanner); Log.Verbose("Found SwapChain via signatures."); Address = sigResolver; } catch (Exception ex) { // The SigScanner method fails on wine/proton since DXGI is not a real DLL. We fall back to vtable to detect our Present function address. Log.Error(ex, "Could not get SwapChain address via sig method, falling back to vtable..."); var vtableResolver = new SwapChainVtableResolver(); vtableResolver.Setup(scanner); Log.Verbose("Found SwapChain via vtable."); Address = vtableResolver; } try { var rtss = NativeFunctions.GetModuleHandle("RTSSHooks64.dll"); if (rtss != IntPtr.Zero) { var fileName = new StringBuilder(255); NativeFunctions.GetModuleFileName(rtss, fileName, fileName.Capacity); this.rtssPath = fileName.ToString(); Log.Verbose("RTSS at {0}", this.rtssPath); if (!NativeFunctions.FreeLibrary(rtss)) { throw new Win32Exception(); } } } catch (Exception e) { Log.Error(e, "RTSS Free failed"); } var setCursorAddr = LocalHook.GetProcAddress("user32.dll", "SetCursor"); Log.Verbose("===== S W A P C H A I N ====="); Log.Verbose("SetCursor address {SetCursor}", setCursorAddr); Log.Verbose("Present address {Present}", Address.Present); Log.Verbose("ResizeBuffers address {ResizeBuffers}", Address.ResizeBuffers); this.setCursorHook = new Hook <SetCursorDelegate>(setCursorAddr, new SetCursorDelegate(SetCursorDetour), this); this.presentHook = new Hook <PresentDelegate>(Address.Present, new PresentDelegate(PresentDetour), this); this.resizeBuffersHook = new Hook <ResizeBuffersDelegate>(Address.ResizeBuffers, new ResizeBuffersDelegate(ResizeBuffersDetour), this); }
public void StringMarshalling() { Assert.Equal('W', NativeFunctions.GetFirstCharacter("Wide-char test")); Assert.Equal((byte)'A', NativeFunctions.GetFirstAnsiCharacter("Ansi-char test")); }
public void ReservedParameter() { Assert.True(NativeFunctions.VerifyReservedParam()); }
public void Execute() { NativeFunctions.CreateRemoteThread(Context.Handle, 0, 0, Address, 0, 0, out int th); Thread = th; }
public PagePanel_Sches(int Width, int Height) : base(Width, Height) { FilesBox = new MListBox() { Bounds = new Rectangle(3, 3, 200, 364) }; UpdateList(); Controls.Add(FilesBox); Button ExecuteButton = new Button() { Text = MainForm.CurrentLanguage["Generate"], Bounds = new Rectangle(204, 3, 90, 30), FlatStyle = FlatStyle.Flat, BackColor = Color.FromArgb(100, 150, 150, 150) }; ExecuteButton.Click += (s, e) => { if (FilesBox.SelectedIndices.Count <= 0) { return; } var ctx = HackContext.GameContext; if (ctx == null) { MessageBox.Show(MainForm.CurrentLanguage["PleaseLockGame"]); return; } string h = $"./Sches/{(string)FilesBox.SelectedItem}.sche"; var bs = SerializeTiles(LoadTilesFromFile(h)); int maddr = NativeFunctions.VirtualAllocEx(ctx.HContext.Handle, 0, bs.Length, NativeFunctions.AllocationType.Commit, NativeFunctions.MemoryProtection.ExecuteReadWrite); NativeFunctions.WriteProcessMemory(ctx.HContext.Handle, maddr, bs, bs.Length, 0); CLRFunctionCaller.Call(ctx, "TRInjections.dll", "TRInjections.ScheMaker.ScheMaker", "LoadTiles", ctx.HContext.MainAddressHelper.GetFunctionAddress("Terraria.Main", "DoUpdate"), maddr); ctx.HContext.GetAddressHelper("TRInjections.dll").SetStaticFieldValue("TRInjections.ScheMaker.ScheMaker", "BrushActive", true); NativeFunctions.VirtualFreeEx(ctx.HContext.Handle, maddr, 0); }; Controls.Add(ExecuteButton); Button CreateNewButton = new Button() { Text = MainForm.CurrentLanguage["Create"], Bounds = new Rectangle(204, 33, 90, 30), FlatStyle = FlatStyle.Flat, BackColor = Color.FromArgb(100, 150, 150, 150) }; CreateNewButton.Click += (s, e) => { MForm CreateNewMForm = new MForm { BackColor = Color.FromArgb(90, 90, 90), Text = MainForm.CurrentLanguage["Create"], StartPosition = FormStartPosition.CenterParent, ClientSize = new Size(245, 52) }; Label NameTip = new Label() { Text = MainForm.CurrentLanguage["Name"] + ":", Location = new Point(0, 0), Size = new Size(80, 20), TextAlign = ContentAlignment.MiddleCenter }; CreateNewMForm.MainPanel.Controls.Add(NameTip); TextBox NameTextBox = new TextBox { BorderStyle = BorderStyle.FixedSingle, BackColor = Color.FromArgb(120, 120, 120), Text = "", Location = new Point(85, 0), Size = new Size(95, 20) }; CreateNewMForm.MainPanel.Controls.Add(NameTextBox); Button ConfirmButton = new Button(); ConfirmButton.Text = MainForm.CurrentLanguage["Confirm"]; ConfirmButton.FlatStyle = FlatStyle.Flat; ConfirmButton.Size = new Size(65, 20); ConfirmButton.Location = new Point(180, 0); ConfirmButton.Click += (s1, e1) => { string str = $"./Sches/{NameTextBox.Text}.sche"; if (!File.Exists(str)) { File.Create(str).Close(); } else { MessageBox.Show(MainForm.CurrentLanguage["NameRepeated"]); } UpdateList(); CreateNewMForm.Dispose(); }; CreateNewMForm.MainPanel.Controls.Add(ConfirmButton); CreateNewMForm.ShowDialog(this); }; Controls.Add(CreateNewButton); Button EditButton = new Button() { Text = MainForm.CurrentLanguage["Edit"], Bounds = new Rectangle(204, 63, 90, 30), FlatStyle = FlatStyle.Flat, BackColor = Color.FromArgb(100, 150, 150, 150) }; EditButton.Click += (s, e) => { if (FilesBox.SelectedIndices.Count <= 0) { return; } ScriptEditorForm p = new ScriptEditorForm((string)FilesBox.SelectedItem); p.Show(); }; Controls.Add(EditButton); Button RenameButton = new Button() { Text = MainForm.CurrentLanguage["Rename"], Bounds = new Rectangle(204, 93, 90, 30), FlatStyle = FlatStyle.Flat, BackColor = Color.FromArgb(100, 150, 150, 150) }; RenameButton.Click += (s, e) => { if (FilesBox.SelectedIndices.Count <= 0) { return; } MForm CreateNewMForm = new MForm { BackColor = Color.FromArgb(90, 90, 90), Text = MainForm.CurrentLanguage["Rename"], StartPosition = FormStartPosition.CenterParent, ClientSize = new Size(245, 52) }; Label NewNameTip = new Label() { Text = MainForm.CurrentLanguage["NewName"] + ":", Location = new Point(0, 0), Size = new Size(80, 20), TextAlign = ContentAlignment.MiddleCenter }; CreateNewMForm.MainPanel.Controls.Add(NewNameTip); TextBox NewNameTextBox = new TextBox { BorderStyle = BorderStyle.FixedSingle, BackColor = Color.FromArgb(120, 120, 120), Text = "", Location = new Point(85, 0), Size = new Size(95, 20) }; NewNameTextBox.Text = (string)FilesBox.SelectedItem; CreateNewMForm.MainPanel.Controls.Add(NewNameTextBox); Button ConfirmButton = new Button(); ConfirmButton.Text = MainForm.CurrentLanguage["Confirm"]; ConfirmButton.FlatStyle = FlatStyle.Flat; ConfirmButton.Size = new Size(65, 20); ConfirmButton.Location = new Point(180, 0); ConfirmButton.Click += (s1, e1) => { string str = $"./Sches/{NewNameTextBox.Text}.sche"; if (!File.Exists(str)) { File.Move($"./Sches/{(string)FilesBox.SelectedItem}.sche", str); } else { MessageBox.Show(MainForm.CurrentLanguage["NameRepeated"]); } UpdateList(); CreateNewMForm.Dispose(); }; CreateNewMForm.MainPanel.Controls.Add(ConfirmButton); CreateNewMForm.ShowDialog(this); }; Controls.Add(RenameButton); Button DeleteButton = new Button() { Text = MainForm.CurrentLanguage["Delete"], Bounds = new Rectangle(204, 123, 90, 30), FlatStyle = FlatStyle.Flat, BackColor = Color.FromArgb(100, 150, 150, 150) }; DeleteButton.Click += (s, e) => { if (FilesBox.SelectedIndices.Count <= 0) { return; } if (MessageBox.Show(MainForm.CurrentLanguage["SureToDelete"], "Warning", MessageBoxButtons.OKCancel) == DialogResult.Cancel) { return; } File.Delete(($"./Sches/{(string)FilesBox.SelectedItem}.sche")); UpdateList(); }; this.Controls.Add(DeleteButton); Button RefreshButton = new Button() { Text = MainForm.CurrentLanguage["Refresh"], Bounds = new Rectangle(204, 153, 90, 30), FlatStyle = FlatStyle.Flat, BackColor = Color.FromArgb(100, 150, 150, 150) }; RefreshButton.Click += (s, e) => { UpdateList(); }; Controls.Add(RefreshButton); }
public MainWindow() { InitializeComponent(); this.textBlock.Text = $"pid:{NativeFunctions.GetCurrentProcessId()}"; }
protected override void Setup() { //敵対関係のグループを作成 chaosRelationShipId = World.AddRelationshipGroup("Inferno:ChaosPeds"); var chaosSettingLoader = new ChaosModeSettingLoader(); chaosModeSetting = chaosSettingLoader.LoadSettingFile(@"ChaosMode_Default.conf"); chaosChecker = new CharacterChaosChecker(chaosModeSetting.DefaultMissionCharacterTreatment, chaosModeSetting.IsChangeMissionCharacterWeapon); defaultWeaponProvider = new CustomWeaponProvider(chaosModeSetting.WeaponList, chaosModeSetting.WeaponListForDriveBy); //キーワードが入力されたらON/OFFを切り替える CreateInputKeywordAsObservable(Keyword) .Subscribe(_ => { IsActive = !IsActive; chaosedPedList.Clear(); StopAllChaosCoroutine(); if (IsActive) { DrawText("ChaosMode:On/" + currentTreatType.ToString(), 3.0f); World.SetRelationshipBetweenGroups(Relationship.Hate, chaosRelationShipId, PlayerPed.RelationshipGroup); } else { DrawText("ChaosMode:Off", 3.0f); World.SetRelationshipBetweenGroups(Relationship.Neutral, chaosRelationShipId, PlayerPed.RelationshipGroup); } }); nextTreatType = currentTreatType; //F7でキャラカオスの切り替え(暫定 OnKeyDownAsObservable .Where(x => IsActive && x.KeyCode == Keys.F7) .Do(_ => { nextTreatType = (MissionCharacterTreatmentType)(((int)nextTreatType + 1) % 3); DrawText("CharacterChaos:" + nextTreatType.ToString(), 1.1f); }) .Throttle(TimeSpan.FromSeconds(1)) .Subscribe(_ => { currentTreatType = nextTreatType; chaosChecker.MissionCharacterTreatment = nextTreatType; DrawText("CharacterChaos:" + currentTreatType.ToString() + "[OK]", 3.0f); chaosedPedList.Clear(); StopAllChaosCoroutine(); }); //interval設定 Interval = chaosModeSetting.Interval; var oneSecondTich = CreateTickAsObservable(TimeSpan.FromSeconds(1)); //市民をカオス化する oneSecondTich .Where(_ => IsActive && PlayerPed.IsSafeExist() && PlayerPed.IsAlive) .Subscribe(_ => CitizenChaos()); //プレイヤが死んだらリセット oneSecondTich .Where(_ => PlayerPed.IsSafeExist()) .Select(_ => PlayerPed.IsDead) .DistinctUntilChanged() .Where(x => x) .Subscribe(_ => { chaosedPedList.Clear(); StopAllChaosCoroutine(); }); oneSecondTich .Where(_ => IsActive) .Subscribe(_ => NativeFunctions.SetAllRandomPedsFlee(Game.Player, false)); //イベントが来たら武器を変更する OnRecievedInfernoEvent .OfType <IEventMessage, ChasoModeEvent>() .Subscribe(e => { if (e is ChangeToDefaultEvent) { singleWeaponProvider = null; } else if (e is ChangeWeaponEvent) { var s = (ChangeWeaponEvent)e; singleWeaponProvider = new SingleWeaponProvider(s.Weapon); } }); }
public void Cleanup() { NativeFunctions.FreeProcessMemory(new IntPtr(m_Memory)); }
static void BlittableFunctionPointers() { Console.WriteLine($"Running {nameof(BlittableFunctionPointers)}..."); IntPtr mod = NativeLibrary.Load(NativeFunctions.GetFullPath()); var cbDefault = NativeLibrary.GetExport(mod, "DoubleInt").ToPointer(); var cbCdecl = NativeLibrary.GetExport(mod, "DoubleIntCdecl").ToPointer(); var cbStdcall = NativeLibrary.GetExport(mod, "DoubleIntStdcall").ToPointer(); const int a = 7; const int expected = a * 2; { // No modopt Console.WriteLine($" -- unmanaged"); int b = CallFunctionPointers.CallUnmanagedIntInt(cbDefault, a); Assert.AreEqual(expected, b); } { Console.WriteLine($" -- unmanaged cdecl"); int b = CallFunctionPointers.CallUnmanagedCdeclIntInt(cbCdecl, a); Assert.AreEqual(expected, b); } { Console.WriteLine($" -- unmanaged stdcall"); int b = CallFunctionPointers.CallUnmanagedStdcallIntInt(cbStdcall, a); Assert.AreEqual(expected, b); } { Console.WriteLine($" -- unmanaged modopt(cdecl)"); int b = CallFunctionPointers.CallUnmanagedIntInt_ModOptCdecl(cbCdecl, a); Assert.AreEqual(expected, b); } { Console.WriteLine($" -- unmanaged modopt(stdcall)"); int b = CallFunctionPointers.CallUnmanagedIntInt_ModOptStdcall(cbStdcall, a); Assert.AreEqual(expected, b); } { // Value in modopt is not a recognized calling convention Console.WriteLine($" -- unmanaged modopt unrecognized"); int b = CallFunctionPointers.CallUnmanagedIntInt_ModOptUnknown(cbDefault, a); Assert.AreEqual(expected, b); } { // Multiple modopts with calling conventions Console.WriteLine($" -- unmanaged modopt(stdcall) modopt(cdecl)"); var ex = Assert.Throws <InvalidProgramException>( () => CallFunctionPointers.CallUnmanagedIntInt_ModOptStdcall_ModOptCdecl(cbCdecl, a), "Multiple modopts with calling conventions should fail"); Assert.AreEqual("Multiple unmanaged calling conventions are specified. Only a single calling convention is supported.", ex.Message); } { Console.WriteLine($" -- unmanaged modopt(stdcall) modopt(unrecognized)"); int b = CallFunctionPointers.CallUnmanagedIntInt_ModOptStdcall_ModOptUnknown(cbStdcall, a); Assert.AreEqual(expected, b); } { Console.WriteLine($" -- unmanaged cdecl modopt(stdcall)"); int b = CallFunctionPointers.CallUnmanagedCdeclIntInt_ModOptStdcall(cbCdecl, a); Assert.AreEqual(expected, b); } { Console.WriteLine($" -- unmanaged stdcall modopt(cdecl)"); int b = CallFunctionPointers.CallUnmanagedStdcallIntInt_ModOptCdecl(cbStdcall, a); Assert.AreEqual(expected, b); } }
public static void Call(GameContext Context, int targetAddr, int hookAddress, params object[] args) { Dictionary <int, int> strAddrs = new Dictionary <int, int>(); object[] trueArgs = args.Select(t => { if (!(t is string) || !(t as string).TrimStart().StartsWith("@")) { return(t); } string str = t as string; string trueStr = str.Substring(str.IndexOf("@") + 1); int strEnd = 0; byte[] bs = Encoding.Unicode.GetBytes(trueStr); int maddr = NativeFunctions.VirtualAllocEx(Context.HContext.Handle, 0, bs.Length + 4, NativeFunctions.AllocationType.Commit, NativeFunctions.MemoryProtection.ExecuteReadWrite); int taddr = NativeFunctions.VirtualAllocEx(Context.HContext.Handle, 0, 4, NativeFunctions.AllocationType.Commit, NativeFunctions.MemoryProtection.ExecuteReadWrite); NativeFunctions.WriteProcessMemory(Context.HContext.Handle, maddr, bs, bs.Length, 0); NativeFunctions.WriteProcessMemory(Context.HContext.Handle, maddr + bs.Length, ref strEnd, 4, 0); strAddrs[taddr] = maddr; return(taddr); }).ToArray(); for (int i = 0; i < args.Length; i++) { var t = args[i]; if (!(t is string) || !(t as string).TrimStart().StartsWith("@")) { trueArgs[i] = args[i]; continue; } string str = t as string; string trueStr = str.Substring(str.IndexOf("@") + 1); int strEnd = 0; byte[] bs = Encoding.Unicode.GetBytes(trueStr); int maddr = NativeFunctions.VirtualAllocEx(Context.HContext.Handle, 0, bs.Length + 4, NativeFunctions.AllocationType.Commit, NativeFunctions.MemoryProtection.ExecuteReadWrite); int taddr = NativeFunctions.VirtualAllocEx(Context.HContext.Handle, 0, 4, NativeFunctions.AllocationType.Commit, NativeFunctions.MemoryProtection.ExecuteReadWrite); NativeFunctions.WriteProcessMemory(Context.HContext.Handle, maddr, bs, bs.Length, 0); NativeFunctions.WriteProcessMemory(Context.HContext.Handle, maddr + bs.Length, ref strEnd, 4, 0); strAddrs[taddr] = maddr; trueArgs[i] = $"dword ptr [{taddr}]"; } AssemblySnippet snippet = AssemblySnippet.FromCode( new AssemblyCode[] { (Instruction)"pushad", AssemblySnippet.FromCode( strAddrs.Select(t => AssemblySnippet.ConstructString( Context.HContext, t.Value, t.Key ))), AssemblySnippet.FromClrCall( targetAddr, null, false, trueArgs), (Instruction)"popad" }); InlineHook.InjectAndWait(Context.HContext, snippet, hookAddress, true); //Console.WriteLine(snippet.GetCode()); foreach (var addrs in strAddrs) { NativeFunctions.VirtualFreeEx(Context.HContext.Handle, addrs.Key, 0); NativeFunctions.VirtualFreeEx(Context.HContext.Handle, addrs.Value, 0); } }
public static void EnableAllRecipes_D(GameContext Context) { NativeFunctions.WriteProcessMemory(Context.HContext.Handle, Context.HContext.MainAddressHelper.GetFunctionAddress("Terraria.Recipe", "FindRecipes"), new byte[] { 0x55 }, 1, 0); }
static void sendFrames(IntPtr device, byte channel) { var frame = new NativeFunctions.candle_frame_t(); { frame.can_id = (deviceID << 19) | (UInt32)NativeFunctions.candle_id_flags.CANDLE_ID_EXTENDED; frame.can_dlc = 7; frame.flags = 0; frame.data = new byte[] { 1, 1, 0, 1, 0, 0, 0, 0, }; } Console.WriteLine("Sending init frame : "); if (!NativeFunctions.candle_frame_send(device, channel, ref frame)) { Console.WriteLine("Failed to send CAN frame"); } Console.WriteLine("Sending moves : "); for (int i = 0; i < 100; i++) { sendMovementFrame(device, channel, i); Console.Write("."); Thread.Sleep(10); } for (int i = 100; i >= 0; i--) { sendMovementFrame(device, channel, i); Console.Write("."); Thread.Sleep(10); } // Send a registry request { frame.data = new byte[] { 0, 1, 0, 0, 0, 0, 0, 0, }; frame.can_dlc = 3; if (!NativeFunctions.candle_frame_send(device, channel, ref frame)) { Console.Write("Failed to send CAN frame"); } } Console.WriteLine("Receiving all : "); int count = 0; while (NativeFunctions.candle_frame_read(device, out frame, 100)) { var id = frame.can_id; if ((id & (UInt32)NativeFunctions.candle_id_flags.CANDLE_ID_EXTENDED) > 0) { Console.Write("E, "); } if ((id & (UInt32)NativeFunctions.candle_id_flags.CANDLE_ID_RTR) > 0) { Console.Write("R, "); } if ((id & (UInt32)NativeFunctions.candle_id_flags.CANDLE_ID_ERR) > 0) { Console.Write("ERR, "); } Console.WriteLine("ID : {0}, DLC : {1}, Data : {2:X},{3:X},{4:X},{5:X},{6:X},{7:X},{8:X},{9:X}, Time : {10}" , id , frame.can_dlc , frame.data[0] , frame.data[1] , frame.data[2] , frame.data[3] , frame.data[4] , frame.data[5] , frame.data[6] , frame.data[7] , frame.timestamp_us / 1000 ); if (count++ > 100) { break; } } }
private static extern bool ValidateRect(IntPtr hWnd, ref NativeFunctions.RECT pRect);
public void Enum() { Assert.Equal(1, (int)NativeFunctions.PassThroughEnum(MyEnum.TestValue)); }