diff --git a/.justfile b/.justfile index 6bf715f..8d4416a 100644 --- a/.justfile +++ b/.justfile @@ -32,8 +32,10 @@ build-server self-contained=isSelfContained: _show-dir rsync -avz --delete ../wwwroot/ ./bin/Release/net9.0/linux-x64/publish/wwwroot/ rsync -avz --delete ../wwwroot/ ./bin/Release/net9.0/win-x64/publish/wwwroot/ +run: run-server + run-server: (build-server "true") - exec ./server/bin/Release/net9.0/linux-x64/publish/server + ./server/bin/Release/net9.0/linux-x64/publish/server run-web: npm run build diff --git a/package.json b/package.json index 85e520b..79175f7 100644 --- a/package.json +++ b/package.json @@ -9,7 +9,7 @@ "preview": "vite preview", "build-only": "vite build", "type-check": "vue-tsc --build", - "pregen-api": "cd server && dotnet run &", + "pregen-api": "cd server && dotnet run --property:Configuration=Release &", "gen-api": "npx nswag openapi2tsclient /input:http://localhost:5000/swagger/v1/swagger.json /output:src/APIClient.ts", "postgen-api": "pkill server" }, diff --git a/src/components/equipments/templates/PG2L100H_Pango100pro.json b/public/EquipmentTemplates/PG2L100H_Pango100pro.json similarity index 100% rename from src/components/equipments/templates/PG2L100H_Pango100pro.json rename to public/EquipmentTemplates/PG2L100H_Pango100pro.json diff --git a/server/Program.cs b/server/Program.cs index fa122ef..a7c74ec 100644 --- a/server/Program.cs +++ b/server/Program.cs @@ -94,13 +94,31 @@ try logger.Info($"Use Static Files : {Path.Combine(Directory.GetCurrentDirectory(), "wwwroot")}"); app.UseDefaultFiles(); app.UseStaticFiles(); // Serves files from wwwroot by default + // Assets Files app.UseStaticFiles(new StaticFileOptions { FileProvider = new PhysicalFileProvider(Path.Combine(Directory.GetCurrentDirectory(), "wwwroot", "assets")), RequestPath = "/assets" }); + // Public Files + app.UseStaticFiles(new StaticFileOptions + { + FileProvider = new PhysicalFileProvider(Path.Combine(Directory.GetCurrentDirectory(), "wwwroot", "EquipmentTemplates")), + RequestPath = "/public/EquipmentTemplates" + }); + // Log Files + if (!Directory.Exists(Path.Combine(Directory.GetCurrentDirectory(), "log"))) + { + Directory.CreateDirectory(Path.Combine(Directory.GetCurrentDirectory(), "log")); + } + app.UseStaticFiles(new StaticFileOptions + { + FileProvider = new PhysicalFileProvider(Path.Combine(Directory.GetCurrentDirectory(), "log")), + RequestPath = "/log" + }); app.MapFallbackToFile("index.html"); } + // Add logs app.UseHttpsRedirection(); app.UseRouting(); app.UseCors(); diff --git a/server/src/RemoteUpdate.cs b/server/src/RemoteUpdateClient.cs similarity index 96% rename from server/src/RemoteUpdate.cs rename to server/src/RemoteUpdateClient.cs index a160b43..df30246 100644 --- a/server/src/RemoteUpdate.cs +++ b/server/src/RemoteUpdateClient.cs @@ -1,8 +1,8 @@ using System.Net; using DotNext; -namespace RemoteUpdate; +namespace RemoteUpdateClient; -static class RemoteUpdateClientAddr +static class RemoteUpdaterAddr { public const UInt32 Base = 0x20_00_00_00; @@ -91,7 +91,7 @@ static class FlashAddr /// /// [TODO:description] /// -public class RemoteUpdateClient +public class RemoteUpdater { private static readonly NLog.Logger logger = NLog.LogManager.GetCurrentClassLogger(); @@ -112,7 +112,7 @@ public class RemoteUpdateClient /// [TODO:parameter] /// [TODO:parameter] /// [TODO:return] - public RemoteUpdateClient(string address, int port, int timeout = 2000, int timeoutForWait = 60 * 1000) + public RemoteUpdater(string address, int port, int timeout = 2000, int timeoutForWait = 60 * 1000) { if (timeout < 0) throw new ArgumentException("Timeout couldn't be negative", nameof(timeout)); @@ -142,7 +142,7 @@ public class RemoteUpdateClient { var ret = await UDPClientPool.WriteAddr( - this.ep, RemoteUpdateClientAddr.WriteCtrl, + this.ep, RemoteUpdaterAddr.WriteCtrl, Convert.ToUInt32((writeSectorNum << 16) | (1 << 15) | Convert.ToInt32(flashAddr / 4096)), this.timeout); if (!ret.IsSuccessful) return new(ret.Error); if (!ret.Value) return new(new Exception("Enable write flash failed")); @@ -150,7 +150,7 @@ public class RemoteUpdateClient { var ret = await UDPClientPool.ReadAddrWithWait( - this.ep, RemoteUpdateClientAddr.WriteSign, + this.ep, RemoteUpdaterAddr.WriteSign, 0x00_00_00_01, 0x00_00_00_01, this.timeoutForWait); if (!ret.IsSuccessful) return new(ret.Error); if (!ret.Value) return new(new Exception( @@ -158,14 +158,14 @@ public class RemoteUpdateClient } { - var ret = await UDPClientPool.WriteAddr(this.ep, RemoteUpdateClientAddr.WriteFIFO, bytesData, this.timeout); + var ret = await UDPClientPool.WriteAddr(this.ep, RemoteUpdaterAddr.WriteFIFO, bytesData, this.timeout); if (!ret.IsSuccessful) return new(ret.Error); if (!ret.Value) return new(new Exception("Send data to flash failed")); } { var ret = await UDPClientPool.ReadAddrWithWait( - this.ep, RemoteUpdateClientAddr.WriteSign, + this.ep, RemoteUpdaterAddr.WriteSign, 0x00_00_01_00, 0x00_00_01_00, this.timeoutForWait); if (!ret.IsSuccessful) return new(ret.Error); return ret.Value; @@ -314,14 +314,14 @@ public class RemoteUpdateClient private async ValueTask> CheckBitstreamCRC(int bitstreamNum, int bitstreamLen, UInt32 checkSum) { { - var ret = await UDPClientPool.WriteAddr(this.ep, RemoteUpdateClientAddr.ReadCtrl2, 0x00_00_00_00, this.timeout); + var ret = await UDPClientPool.WriteAddr(this.ep, RemoteUpdaterAddr.ReadCtrl2, 0x00_00_00_00, this.timeout); if (!ret.IsSuccessful) return new(ret.Error); if (!ret.Value) return new(new Exception("Write read control 2 failed")); } { var ret = await UDPClientPool.WriteAddr( - this.ep, RemoteUpdateClientAddr.ReadCtrl1, + this.ep, RemoteUpdaterAddr.ReadCtrl1, Convert.ToUInt32((bitstreamLen << 16) | (1 << 15) | Convert.ToInt32(FlashAddr.Bitstream[bitstreamNum] / 4096)), this.timeout); if (!ret.IsSuccessful) return new(ret.Error); @@ -330,7 +330,7 @@ public class RemoteUpdateClient { var ret = await UDPClientPool.ReadAddrWithWait( - this.ep, RemoteUpdateClientAddr.ReadSign, + this.ep, RemoteUpdaterAddr.ReadSign, 0x00_00_01_00, 0x00_00_01_00, this.timeoutForWait); if (!ret.IsSuccessful) return new(ret.Error); if (!ret.Value) return new(new Exception( @@ -338,7 +338,7 @@ public class RemoteUpdateClient } { - var ret = await UDPClientPool.ReadAddr(this.ep, RemoteUpdateClientAddr.ReadCRC, this.timeout); + var ret = await UDPClientPool.ReadAddr(this.ep, RemoteUpdaterAddr.ReadCRC, this.timeout); if (!ret.IsSuccessful) return new(ret.Error); var bytes = ret.Value.Options.Data; @@ -368,7 +368,7 @@ public class RemoteUpdateClient $"Bitsteam num should be 0 ~ 3 for HotRest, but given {bitstreamNum}", nameof(bitstreamNum))); var ret = await UDPClientPool.WriteAddr( - this.ep, RemoteUpdateClientAddr.HotResetCtrl, + this.ep, RemoteUpdaterAddr.HotResetCtrl, ((FlashAddr.Bitstream[bitstreamNum] << 8) | 1), this.timeout); if (!ret.IsSuccessful) return new(ret.Error); return ret.Value; @@ -542,7 +542,7 @@ public class RemoteUpdateClient logger.Trace("Clear udp data finished"); { - var ret = await UDPClientPool.ReadAddr(this.ep, RemoteUpdateClientAddr.Version, this.timeout); + var ret = await UDPClientPool.ReadAddr(this.ep, RemoteUpdaterAddr.Version, this.timeout); if (!ret.IsSuccessful) return new(ret.Error); var retData = ret.Value.Options.Data; diff --git a/src/APIClient.ts b/src/APIClient.ts index bdd3396..3fa3f2c 100644 --- a/src/APIClient.ts +++ b/src/APIClient.ts @@ -1394,7 +1394,6 @@ export interface ISystemException extends IException { } export class ArgumentException extends SystemException implements IArgumentException { - message?: string; paramName?: string | undefined; constructor(data?: IArgumentException) { @@ -1471,4 +1470,4 @@ function throwException(message: string, status: number, response: string, heade throw result; else throw new ApiException(message, status, response, headers, null); -} \ No newline at end of file +} diff --git a/src/components/ComponentSelector.vue b/src/components/ComponentSelector.vue index be4779c..31f1b4a 100644 --- a/src/components/ComponentSelector.vue +++ b/src/components/ComponentSelector.vue @@ -5,10 +5,13 @@ - + + - + @@ -16,55 +19,53 @@ 添加元器件 - + - + - 元器件 + 元器件 模板 虚拟外设 - + - - + + - 搜索 + + 搜索 + - + + class="card bg-base-200 hover:bg-base-300 transition-all duration-300 hover:shadow-md cursor-pointer" + @click="addComponent(component)"> - + - + 加载中... @@ -75,7 +76,9 @@ - + @@ -86,25 +89,31 @@ - + + class="card bg-base-200 hover:bg-base-300 transition-all duration-300 hover:shadow-md cursor-pointer" + @click="addTemplate(template)"> - - + + {{ template.name }} - {{ template.description || '模板' }} + + {{ template.description || "模板" }} + - + @@ -115,21 +124,18 @@ - + + class="card bg-base-200 hover:bg-base-300 transition-all duration-300 hover:shadow-md cursor-pointer" + @click="addComponent(device)"> - + - + 加载中... @@ -140,7 +146,9 @@ - + @@ -151,11 +159,12 @@ - + - + 返回 @@ -171,7 +180,8 @@ diff --git a/src/views/AdminView.vue b/src/views/AdminView.vue index 6b7a691..71d7187 100644 --- a/src/views/AdminView.vue +++ b/src/views/AdminView.vue @@ -1,8 +1,8 @@ - + FPGA 设备管理 - { isEditMode = !isEditMode; } @@ -13,16 +13,19 @@ - IP 地址列表 + + IP 地址列表 + 刷新 + - IP 地址 - 版本号 - 默认启动位流 + IP 地址 + 版本号 + 默认启动位流 黄金位流 应用位流1 应用位流2 @@ -35,7 +38,7 @@ - + {{ devAddr }} v1.2.3 @@ -50,29 +53,25 @@ - + - + - + - + @@ -138,7 +137,7 @@ const devPort = 1234; const remoteUpdater = new RemoteUpdaterClient(); // 处理文件上传 -function handleFileChange(event: Event, fileRef: any) { +function handleFileChange(event: Event, bistreamNum: number) { const target = event.target as HTMLInputElement; const file = target.files?.[0]; // 获取选中的第一个文件 @@ -146,8 +145,16 @@ function handleFileChange(event: Event, fileRef: any) { return; } - if (!isUndefined(fileRef)) { - fileRef.value = file; + if (bistreamNum === 0) { + goldBitstreamFile.value = file; + } else if (bistreamNum === 1) { + appBitstream1File.value = file; + } else if (bistreamNum === 2) { + appBitstream2File.value = file; + } else if (bistreamNum === 3) { + appBitstream3File.value = file; + } else { + goldBitstreamFile.value = file; } } @@ -172,12 +179,13 @@ async function uploadAndDownloadBitstreams( appBitstream3?: File, ) { let cnt = 0; - if (isUndefined(goldBitstream)) cnt++; - if (isUndefined(appBitstream1)) cnt++; - if (isUndefined(appBitstream2)) cnt++; - if (isUndefined(appBitstream3)) cnt++; - if ((cnt = 0)) { + if (!isUndefined(goldBitstream)) cnt++; + if (!isUndefined(appBitstream1)) cnt++; + if (!isUndefined(appBitstream2)) cnt++; + if (!isUndefined(appBitstream3)) cnt++; + if (cnt === 0) { dialog.error("未选择比特流"); + return; } try { @@ -189,10 +197,9 @@ async function uploadAndDownloadBitstreams( Common.toFileParameterOrNull(appBitstream2), Common.toFileParameterOrNull(appBitstream3), ); - if (ret) { + if (!ret) { dialog.warn("上传比特流出错"); - } else { - dialog.info("上传比特流成功"); + return; } } { @@ -230,6 +237,15 @@ async function hotresetBitstream(devAddr: string, bitstreamNum: number) { console.error(e); } } + +async function refreshData() { + try { + const ret = await remoteUpdater.getFirmwareVersion(devAddr.value, devPort); + } catch (e) { + dialog.error("获取数据失败"); + console.error(e); + } +}
{{ template.description || '模板' }}
+ {{ template.description || "模板" }} +