diff --git a/ide/server/smarperfServer.py b/ide/server/smarperfServer.py index 2f30cb886a770446a588bd3ccd2df6c3f313cc08..d3d0ffc214351a7e325ee2d39da85091fe314310 100644 --- a/ide/server/smarperfServer.py +++ b/ide/server/smarperfServer.py @@ -161,19 +161,19 @@ class SpRequestHandler(http.server.BaseHTTPRequestHandler): nowDate = datetime.now() now = nowDate.strftime("%Y-%m-%d") fileName = f"{now}.txt" - dst = open("./logger/" + fileName, "a") - content_type = self.headers.get("Content-Type") - if content_type and content_type.startswith("application/json"): - content_length = int(self.headers.get("Content-Length", 0)) - req_data = self.rfile.read(content_length) - req = json.loads(req_data) - now = datetime.now() - formatted_date = now.strftime("%Y-%m-%d %H:%M:%S") - dst.write(f"{formatted_date} {req['fileName']} ({req['fileSize']} M)\n") - self.send_response(200) - self.send_header("Content-type", "text/html") - self.end_headers() - self.wfile.write(bytes(f"日志写入成功", "utf-8")) + with open("./logger/" + fileName, "a") as dst: + content_type = self.headers.get("Content-Type") + if content_type and content_type.startswith("application/json"): + content_length = int(self.headers.get("Content-Length", 0)) + req_data = self.rfile.read(content_length) + req = json.loads(req_data) + now = datetime.now() + formatted_date = now.strftime("%Y-%m-%d %H:%M:%S") + dst.write(f"{formatted_date} {req['fileName']} ({req['fileSize']} M)\n") + self.send_response(200) + self.send_header("Content-type", "text/html") + self.end_headers() + self.wfile.write(bytes(f"日志写入成功", "utf-8")) def check_dir(self, dir_path): if not os.path.exists(dir_path): diff --git a/ide/src/trace/component/trace/timer-shaft/RangeRuler.ts b/ide/src/trace/component/trace/timer-shaft/RangeRuler.ts index d6446a750ffebebfafa3d788b4b586f100d685a5..52b685050ae327e3c923ae790841c47ab3bc18f3 100644 --- a/ide/src/trace/component/trace/timer-shaft/RangeRuler.ts +++ b/ide/src/trace/component/trace/timer-shaft/RangeRuler.ts @@ -18,7 +18,7 @@ import { Rect } from './Rect.js'; import { ns2s, ns2UnitS, TimerShaftElement } from '../TimerShaftElement.js'; import { ColorUtils } from '../base/ColorUtils.js'; import { CpuStruct } from '../../../database/ui-worker/ProcedureWorkerCPU.js'; -import {CurrentSlicesTime, SpSystemTrace} from '../../SpSystemTrace.js'; +import { CurrentSlicesTime, SpSystemTrace } from '../../SpSystemTrace.js'; const MarkPadding = 5; const FIT_TOTALX_MIN: number = 280; @@ -543,21 +543,26 @@ export class RangeRuler extends Graph { sliceMidX = Math.round(startX + totalX / 2); let count1 = 0; let count2 = 0; - let sliceMidXMap = new Map(); let animF = () => { + let sliceMidXMap = new Map(); startX = (this.rulerW * (startTime - this.range.startNS)) / (this.range.endNS - this.range.startNS); endX = (this.rulerW * (endTime - this.range.startNS)) / (this.range.endNS - this.range.startNS); - totalX = Math.round(endX - startX); + totalX = endX - startX; sliceMidX = Math.round(startX + totalX / 2); let x = 1; do { startX = (this.rulerW * (startTime - this.range.startNS)) / (this.range.endNS - this.range.startNS); endX = (this.rulerW * (endTime - this.range.startNS)) / (this.range.endNS - this.range.startNS); - totalX = Math.round(endX - startX); + totalX = endX - startX; sliceMidX = Math.round(startX + (endX - startX) / 2); - if (sliceMidX !== sliceMidXMap.get('tempMid1') && sliceMidX !== sliceMidXMap.get('tempMid2')) { + if (totalX === 0) { + return; + } + // 修正sliceMidX的值 + if (sliceMidX !== sliceMidXMap.get('tempMid1') || 0 + && sliceMidX !== sliceMidXMap.get('tempMid2') || 0) { if (x % 2 === 0) { - sliceMidXMap.set('tempMid2', sliceMidX); // 偶数 + sliceMidXMap.set('tempMid2', sliceMidX); // 偶数 } else { sliceMidXMap.set('tempMid1', sliceMidX); // 奇数 } @@ -565,76 +570,138 @@ export class RangeRuler extends Graph { if (sliceMidX === sliceMidXMap.get('tempMid1')) { count1++; } + if (sliceMidX === sliceMidXMap.get('tempMid2')) { count2++; } - } - if (count1 >= 10 || count2 >= 10) { - let tempMid1 = sliceMidXMap.get('tempMid1') || 0; - let tempMid2 = sliceMidXMap.get('tempMid2') || 0; - if (sliceMidX === tempMid1 && tempMid1 === tempMid2) { - sliceMidX += 11; - } - if (sliceMidX === tempMid1 && sliceMidX !== tempMid2) { - if (sliceMidX < tempMid2) { - sliceMidX += 15; - } else { - sliceMidX -= 10; + // 此处为了解决特殊情况下sliceMidX的值非常接近中间区域,但是又无法进入中间区域,导致死循环程序无法正常终止。 + if (count1 >= 3 && count1 <= 5 + || count2 >= 3 && count2 <= 5) { + if (sliceMidX >= midX - MID_OFFSET && sliceMidX <= midX + MID_OFFSET) { + let tempMid1 = sliceMidXMap.get('tempMid1') || 0; + let tempMid2 = sliceMidXMap.get('tempMid2') || 0; + if (sliceMidX === tempMid1 + && tempMid1 === tempMid2) { + sliceMidX += 11; + } + if (sliceMidX === tempMid1 + && sliceMidX !== tempMid2) { + if (sliceMidX < tempMid2) { + sliceMidX += 15; + } else { + sliceMidX -= 10; + } + } + if (sliceMidX === tempMid2 && sliceMidX !== tempMid1) { + if (sliceMidX < tempMid1) { + sliceMidX += 15; + } else { + sliceMidX -= 10; + } + } } } - if (sliceMidX === tempMid2 && sliceMidX !== tempMid1) { - if (sliceMidX < tempMid1) { - sliceMidX += 15; - } else { - sliceMidX -= 10; - } + if (count1 > 5 || count2 > 5) { + this.fillX(); + this.range.refresh = true; + this.notifyHandler(this.range); + this.range.refresh = false; + return; } } x++; if (sliceMidX >= midX - MID_OFFSET && sliceMidX <= midX + MID_OFFSET) { - if ((totalX < FIT_TOTALX_MIN && totalX >= 0) || totalX > FIT_TOTALX_MAX) { + /* 把 endNS 转换为 endX , startNS 转化 startX, + totalX = ( endX - startX ) 280px <= totalX <= 300px + 此时,如果slice的比例或者宽度不合适,则进行调整校正,缩放到合适的比例。 + 不能使用固定的 scale, 因为调整slice的宽度时,scale、 startNS 和 endNS 都在变化, + 所以要使用 totalX 来判断slice是否缩放到合适的大小了。 + */ + if (totalX < FIT_TOTALX_MIN - MID_OFFSET && totalX > 0 + || Math.round(totalX) > FIT_TOTALX_MAX + MID_OFFSET) { this.zoomFit(startTime, endTime); + this.fillX(); + this.range.refresh = true; + this.notifyHandler(this.range); + this.range.refresh = false; } - this.fillX(); - this.range.refresh = true; - this.notifyHandler(this.range); - this.range.refresh = false; - return; - } - let s = (this.scale / this.p) * this.currentDuration * 0.2; - let big_s = (this.scale / this.p) * this.currentDuration * 1.2; - if (sliceMidX > midX + MID_OFFSET) { - let distance = sliceMidX - midX; - if (distance > DIS) { - this.range.startNS += big_s; - this.range.endNS += big_s; - } else { - this.range.startNS += s; - this.range.endNS += s; + startX = (this.rulerW * (startTime - this.range.startNS)) / (this.range.endNS - this.range.startNS); + endX = (this.rulerW * (endTime - this.range.startNS)) / (this.range.endNS - this.range.startNS); + totalX = endX - startX; + sliceMidX = Math.round(startX + (endX - startX) / 2); + if (sliceMidX >= midX - MID_OFFSET + && sliceMidX <= midX + MID_OFFSET + && Math.round(totalX) >= FIT_TOTALX_MIN - MID_OFFSET + && Math.round(totalX) <= FIT_TOTALX_MAX + MID_OFFSET) { + this.fillX(); + this.range.refresh = true; + this.notifyHandler(this.range); + this.range.refresh = false; + return; } - } - if (sliceMidX < midX - MID_OFFSET) { - let distance = midX - sliceMidX; // 28.5 - if (distance > DIS) { - this.range.startNS -= big_s; - this.range.endNS -= big_s; - } else { - this.range.startNS -= s; - this.range.endNS -= s; + } else { + // 0.2经验值,不要随便调整这个系数,该系数决定了调整后的slice中间位置是否能落在FIT_TOTALX_MIN和FIT_TOTALX_MAX之间。 + let s = (this.scale / this.p) * this.currentDuration * 0.2; // 微调 + let big_s = (this.scale / this.p) * this.currentDuration * 1.2; // 大幅度调整 + let biger = (this.scale / this.p) * this.currentDuration * 10; // 更大幅度调整 + let huge = (this.scale / this.p) * this.currentDuration * 100; // 巨大幅度调整 + startX = (this.rulerW * (startTime - this.range.startNS)) / (this.range.endNS - this.range.startNS); + endX = (this.rulerW * (endTime - this.range.startNS)) / (this.range.endNS - this.range.startNS); + totalX = endX - startX; + sliceMidX = Math.round(startX + (endX - startX) / 2); + // slice中间位置大于画布的中间坐标时画布右移 ,startNS + s + if (sliceMidX > midX + MID_OFFSET) { + let distance = sliceMidX - midX; + if (distance >= 10000) { + this.range.startNS += huge; + this.range.endNS += huge; + } + else if (distance >= 1000 && distance < 10000) { + this.range.startNS += biger; + this.range.endNS += biger; + } + else if (distance > DIS && distance < 1000) { + this.range.startNS += big_s; + this.range.endNS += big_s; + } else { + this.range.startNS += s; + this.range.endNS += s; + } + } + // slice中间位置小于画布的中间坐标时画布左移, startNS - s + if (sliceMidX < midX - MID_OFFSET) { + let distance = midX - sliceMidX; // 28.5 + if (distance >= 10000) { + this.range.startNS -= huge; + this.range.endNS -= huge; + } + else if (distance >= 1000 && distance < 10000) { + this.range.startNS -= biger; + this.range.endNS -= biger; + } + else if (distance > DIS && distance < 1000) { + this.range.startNS -= big_s; + this.range.endNS -= big_s; + } else { + this.range.startNS -= s; + this.range.endNS -= s; + } } } this.fillX(); this.draw(); this.range.refresh = false; - } while (sliceMidX < midX - MID_OFFSET || sliceMidX > midX + MID_OFFSET); + } while (sliceMidX < midX - MID_OFFSET || sliceMidX > midX + MID_OFFSET + || Math.round(totalX) < FIT_TOTALX_MIN - MID_OFFSET + || Math.round(totalX) > FIT_TOTALX_MAX + MID_OFFSET) this.pressFrameIdF = requestAnimationFrame(animF); }; - if (totalX <= 3) { + if (totalX < FIT_TOTALX_MIN - MID_OFFSET && totalX > 0 || totalX > FIT_TOTALX_MAX + MID_OFFSET) { this.zoomFit(startTime, endTime); this.pressFrameIdF = requestAnimationFrame(animF); } - this.zoomFit(startTime, endTime); this.pressFrameIdF = requestAnimationFrame(animF); + this.zoomFit(startTime, endTime); } keyPressW() { let animW = () => { @@ -856,61 +923,88 @@ export class RangeRuler extends Graph { zoomFit(startTime: number, endTime: number) { let startX = (this.rulerW * (startTime - this.range.startNS)) / (this.range.endNS - this.range.startNS); let endX = (this.rulerW * (endTime - this.range.startNS)) / (this.range.endNS - this.range.startNS); - let totalX = Math.round(endX - startX); + let totalX = endX - startX; this.centerXPercentage = 0.5; let clientWidth = this.canvas?.clientWidth || 0; // 1424 let midX = Math.round(clientWidth / 2); this.currentDuration = 1000; - let totalXMap = new Map(); let count1 = 0; let count2 = 0; let animW = () => { - if (this.scale === 50) { + startX = Math.round((this.rulerW * (startTime - this.range.startNS)) / (this.range.endNS - this.range.startNS)); + endX = Math.round((this.rulerW * (endTime - this.range.startNS)) / (this.range.endNS - this.range.startNS)); + totalX = endX - startX; + if (Math.round(totalX) !== totalXMap.get('totalX1')) { + totalXMap.set('totalX1', Math.round(totalX)); + } else { + if (Math.round(totalX) === totalXMap.get('totalX1')) { + count1++; + } + } + if (count1 >= 3 && count1 <= 5) { + if (Math.round(totalX) >= FIT_TOTALX_MIN - MID_OFFSET + && Math.round(totalX) <= FIT_TOTALX_MAX + MID_OFFSET) { + let tempTotalX1 = totalXMap.get('totalX1') || 0; + let tempTotalX2 = totalXMap.get('totalX2') || 0; + if (Math.round(totalX) === tempTotalX1 + && tempTotalX2 === tempTotalX2) { + totalX += 11; + } + if (Math.round(totalX) === tempTotalX1 + && Math.round(totalX) !== tempTotalX2) { + if (Math.round(totalX) < tempTotalX2) { + totalX += 12; + } else { + totalX -= 11; + } + } + if (Math.round(totalX) === tempTotalX2 && Math.round(totalX) !== tempTotalX1) { + if (Math.round(totalX) < tempTotalX1) { + totalX += 12; + } else { + totalX -= 11; + } + } + } + } + // 此处为了解决特殊情况下sliceMidX的值非常接近中间区域,但是又无法进入中间区域,导致死循环程序无法正常终止。 + if (count1 > 5) { this.fillX(); this.range.refresh = true; this.notifyHandler(this.range); this.range.refresh = false; + // 如果出现循环缩放,则退出。 return; } - if (totalX < 5 && this.scale >= 10_000_000) { - for (let i = 0; i < 15; i++) { - this.range.startNS += (this.centerXPercentage * this.currentDuration * this.scale) / this.p; - this.range.endNS -= ((1 - this.centerXPercentage) * this.currentDuration * this.scale) / this.p; - } - } else if (totalX < 100 && this.scale >= 10_000) { - for (let i = 0; i < 10; i++) { - this.range.startNS += (this.centerXPercentage * this.currentDuration * this.scale) / this.p; - this.range.endNS -= ((1 - this.centerXPercentage) * this.currentDuration * this.scale) / this.p; - } - } else { - this.range.startNS += (this.centerXPercentage * this.currentDuration * this.scale) / this.p; - this.range.endNS -= ((1 - this.centerXPercentage) * this.currentDuration * this.scale) / this.p; - } - this.fillX(); - this.draw(); - startX = (this.rulerW * (startTime - this.range.startNS)) / (this.range.endNS - this.range.startNS); - endX = (this.rulerW * (endTime - this.range.startNS)) / (this.range.endNS - this.range.startNS); - totalX = Math.round(endX - startX); - if (totalX !== totalXMap.get('totalX1')) { - totalXMap.set('totalX1', totalX); - } else { - if (totalX === totalXMap.get('totalX1')) { - count1++; + if (totalX >= FIT_TOTALX_MIN - MID_OFFSET && totalX <= FIT_TOTALX_MAX + MID_OFFSET) { + let sliceMidX = Math.round(startX + totalX / 2); + if (sliceMidX < midX - MID_OFFSET || sliceMidX > midX + MID_OFFSET) { + this.keyPressF(); + } else { + this.fillX(); + this.range.refresh = true; + this.notifyHandler(this.range); + this.range.refresh = false; + return; } } - if (totalX >= FIT_TOTALX_MIN && totalX <= FIT_TOTALX_MAX) { + if (this.scale === 50) { this.fillX(); this.range.refresh = true; this.notifyHandler(this.range); this.range.refresh = false; return; } - if (totalX > FIT_TOTALX_MAX) { - if (count1 >= 10) { - return; - } - this.pressFrameIdS = requestAnimationFrame(animS); + this.range.startNS += (this.centerXPercentage * this.currentDuration * this.scale) / this.p; + this.range.endNS -= ((1 - this.centerXPercentage) * this.currentDuration * this.scale) / this.p; + this.fillX(); + this.draw(); + this.range.refresh = false; + startX = (this.rulerW * (startTime - this.range.startNS)) / (this.range.endNS - this.range.startNS); + endX = (this.rulerW * (endTime - this.range.startNS)) / (this.range.endNS - this.range.startNS); + totalX = Math.round(endX - startX); + if (totalX >= FIT_TOTALX_MAX + MID_OFFSET) { this.fillX(); this.range.refresh = true; this.notifyHandler(this.range); @@ -923,45 +1017,68 @@ export class RangeRuler extends Graph { startX = Math.round((this.rulerW * (startTime - this.range.startNS)) / (this.range.endNS - this.range.startNS)); endX = Math.round((this.rulerW * (endTime - this.range.startNS)) / (this.range.endNS - this.range.startNS)); totalX = endX - startX; - if (totalX >= FIT_TOTALX_MIN && totalX <= FIT_TOTALX_MAX) { + if (Math.round(totalX) !== totalXMap.get('totalX2')) { + totalXMap.set('totalX2', Math.round(totalX)); + } else { + if (Math.round(totalX) === totalXMap.get('totalX2')) { + count2++; + } + } + if (count2 >= 3 && count2 <= 5) { + if (Math.round(totalX) >= FIT_TOTALX_MIN - MID_OFFSET + && Math.round(totalX) <= FIT_TOTALX_MAX + MID_OFFSET) { + let tempTotalX1 = totalXMap.get('totalX1') || 0; + let tempTotalX2 = totalXMap.get('totalX2') || 0; + if (Math.round(totalX) === tempTotalX1 + && tempTotalX2 === tempTotalX2) { + totalX += 11; + } + if (Math.round(totalX) === tempTotalX1 + && Math.round(totalX) !== tempTotalX2) { + if (Math.round(totalX) < tempTotalX2) { + totalX += 12; + } else { + totalX -= 11; + } + } + if (Math.round(totalX) === tempTotalX2 && Math.round(totalX) !== tempTotalX1) { + if (Math.round(totalX) < tempTotalX1) { + totalX += 12; + } else { + totalX -= 11; + } + } + } + } + if (count2 > 5) { this.fillX(); this.range.refresh = true; this.notifyHandler(this.range); this.range.refresh = false; + // 如果出现循环缩放,则退出。 return; } - if (totalX > midX) { - for (let i = 0; i < 10; i++) { - this.range.startNS -= ((this.centerXPercentage * this.scale) / this.p) * this.currentDuration; - this.range.endNS += (((1 - this.centerXPercentage) * this.scale) / this.p) * this.currentDuration; - } - } else if (totalX >= 500) { - for (let i = 0; i < 5; i++) { - this.range.startNS -= ((this.centerXPercentage * this.scale) / this.p) * this.currentDuration; - this.range.endNS += (((1 - this.centerXPercentage) * this.scale) / this.p) * this.currentDuration; + if (totalX >= FIT_TOTALX_MIN - MID_OFFSET && totalX <= FIT_TOTALX_MAX + MID_OFFSET) { + let sliceMidX = Math.round(startX + totalX / 2); + if (sliceMidX < midX - MID_OFFSET || sliceMidX > midX + MID_OFFSET) { + this.keyPressF(); + } else { + this.fillX(); + this.range.refresh = true; + this.notifyHandler(this.range); + this.range.refresh = false; + return; } - } else { - this.range.startNS -= ((this.centerXPercentage * this.scale) / this.p) * this.currentDuration; - this.range.endNS += (((1 - this.centerXPercentage) * this.scale) / this.p) * this.currentDuration; } + this.range.startNS -= ((this.centerXPercentage * this.scale) / this.p) * this.currentDuration; + this.range.endNS += (((1 - this.centerXPercentage) * this.scale) / this.p) * this.currentDuration; this.fillX(); this.draw(); this.range.refresh = false; startX = Math.round((this.rulerW * (startTime - this.range.startNS)) / (this.range.endNS - this.range.startNS)); endX = Math.round((this.rulerW * (endTime - this.range.startNS)) / (this.range.endNS - this.range.startNS)); - totalX = endX - startX; - if (totalX !== totalXMap.get('totalX2')) { - totalXMap.set('totalX2', totalX); - } else { - if (totalX === totalXMap.get('totalX2')) { - count2++; - } - } - if (totalX <= FIT_TOTALX_MIN) { - if (count2 >= 10) { - return; - } - this.pressFrameIdW = requestAnimationFrame(animW); + totalX = Math.round(endX - startX); + if (totalX <= FIT_TOTALX_MIN - MID_OFFSET) { this.fillX(); this.range.refresh = true; this.notifyHandler(this.range); @@ -970,10 +1087,10 @@ export class RangeRuler extends Graph { } this.pressFrameIdS = requestAnimationFrame(animS); }; - if (totalX > FIT_TOTALX_MAX) { + if (Math.round(totalX) > FIT_TOTALX_MAX + MID_OFFSET) { this.pressFrameIdS = requestAnimationFrame(animS); } - if (totalX < FIT_TOTALX_MIN && totalX >= 0) { + if (totalX < FIT_TOTALX_MIN - MID_OFFSET) { this.pressFrameIdW = requestAnimationFrame(animW); } } diff --git a/trace_streamer/build/protoc_w.sh b/trace_streamer/build/protoc_w.py similarity index 100% rename from trace_streamer/build/protoc_w.sh rename to trace_streamer/build/protoc_w.py