From c997c3d352aff47edf81615c08d595fab581c9e3 Mon Sep 17 00:00:00 2001 From: Yin Zhang Date: Fri, 28 Feb 2025 11:58:04 -0800 Subject: [PATCH] revamp on op_profile tool, no functional change. PiperOrigin-RevId: 732212351 --- frontend/app/components/op_profile/BUILD | 47 +++++++--- .../components/op_profile/op_details/BUILD | 1 + .../op_profile/op_details/op_details.ng.html | 9 +- .../op_profile/op_details/op_details.ts | 29 +++---- .../components/op_profile/op_profile.ng.html | 82 ++---------------- .../app/components/op_profile/op_profile.scss | 3 - .../app/components/op_profile/op_profile.ts | 56 ++++++------ .../op_profile/op_profile_base.ng.html | 85 +++++++++++++++++++ .../components/op_profile/op_profile_base.ts | 74 +++++++++++++--- .../op_profile/op_profile_base_module.ts | 29 +++++++ .../op_profile/op_profile_common.scss | 10 +++ .../components/op_profile/op_profile_data.ts | 8 +- .../op_profile/op_profile_module.ts | 18 ++-- .../app/components/sidenav/sidenav.ng.html | 4 - frontend/app/services/data_service_v2/BUILD | 3 + .../data_service_v2/data_service_v2.ts | 19 +++++ .../data_service_v2_interface.ts | 6 ++ 17 files changed, 310 insertions(+), 173 deletions(-) delete mode 100644 frontend/app/components/op_profile/op_profile.scss create mode 100644 frontend/app/components/op_profile/op_profile_base.ng.html create mode 100644 frontend/app/components/op_profile/op_profile_base_module.ts diff --git a/frontend/app/components/op_profile/BUILD b/frontend/app/components/op_profile/BUILD index 0cbb32bf5..dcc846e6a 100644 --- a/frontend/app/components/op_profile/BUILD +++ b/frontend/app/components/op_profile/BUILD @@ -11,7 +11,7 @@ xprof_ng_module( "op_profile_module.ts", ], assets = [ - ":op_profile_css", + ":op_profile_common_css", "op_profile.ng.html", ], # strict_templates = False, @@ -21,40 +21,52 @@ xprof_ng_module( "@npm//@angular/router", "@npm//@ngrx/store", "@npm//rxjs", - "@org_xprof//frontend/app/common/angular:angular_material_form_field", - "@org_xprof//frontend/app/common/angular:angular_material_icon", - "@org_xprof//frontend/app/common/angular:angular_material_input", - "@org_xprof//frontend/app/common/angular:angular_material_slide_toggle", - "@org_xprof//frontend/app/common/angular:angular_material_tooltip", "@org_xprof//frontend/app/common/interfaces", - "@org_xprof//frontend/app/components/op_profile/op_table", + "@org_xprof//frontend/app/common/utils", + "@org_xprof//frontend/app/components/op_profile/op_details", "@org_xprof//frontend/app/services/data_service", "@org_xprof//frontend/app/store", ], ) -ts_library( +xprof_ng_module( name = "op_profile_base", srcs = [ "op_profile_base.ts", - "op_profile_data.ts", + "op_profile_base_module.ts", + ], + assets = [ + "op_profile_base.ng.html", + ":op_profile_common_css", ], deps = [ + ":op_profile_data", + "@npm//@angular/core", + "@npm//@angular/router", "@npm//@ngrx/store", + "@npm//rxjs", + "@org_xprof//frontend/app/common/angular:angular_material_form_field", + "@org_xprof//frontend/app/common/angular:angular_material_icon", + "@org_xprof//frontend/app/common/angular:angular_material_input", + "@org_xprof//frontend/app/common/angular:angular_material_sidenav", + "@org_xprof//frontend/app/common/angular:angular_material_slide_toggle", + "@org_xprof//frontend/app/common/angular:angular_material_tooltip", "@org_xprof//frontend/app/common/interfaces", "@org_xprof//frontend/app/common/interfaces:op_profile_proto_defs", "@org_xprof//frontend/app/common/utils", + "@org_xprof//frontend/app/components/op_profile/op_table", + "@org_xprof//frontend/app/services/data_service_v2:data_service_v2_interface", "@org_xprof//frontend/app/store", ], ) sass_binary( - name = "op_profile_css", - src = "op_profile.scss", + name = "op_profile_common_css", + src = "op_profile_common.scss", # stack = False, sourcemap = False, deps = [ - ":op_profile_common", + "@org_xprof//frontend/app/styles:common", ], ) @@ -65,3 +77,14 @@ sass_library( "@org_xprof//frontend/app/styles:common", ], ) + +ts_library( + name = "op_profile_data", + srcs = [ + "op_profile_data.ts", + ], + deps = [ + "@org_xprof//frontend/app/common/interfaces:op_profile_proto_defs", + "@org_xprof//frontend/app/common/utils", + ], +) diff --git a/frontend/app/components/op_profile/op_details/BUILD b/frontend/app/components/op_profile/op_details/BUILD index 88ee76221..d75e373ee 100644 --- a/frontend/app/components/op_profile/op_details/BUILD +++ b/frontend/app/components/op_profile/op_details/BUILD @@ -26,6 +26,7 @@ xprof_ng_module( "@org_xprof//frontend/app/common/interfaces:op_profile_proto_defs", "@org_xprof//frontend/app/common/utils", "@org_xprof//frontend/app/services/communication_service", + "@org_xprof//frontend/app/services/data_service_v2:data_service_v2_interface", "@org_xprof//frontend/app/store", ], ) diff --git a/frontend/app/components/op_profile/op_details/op_details.ng.html b/frontend/app/components/op_profile/op_details/op_details.ng.html index 27a852511..630f974c0 100644 --- a/frontend/app/components/op_profile/op_details/op_details.ng.html +++ b/frontend/app/components/op_profile/op_details/op_details.ng.html @@ -12,7 +12,7 @@
- -
-

Utilization may have been capped at 100% as accurate bandwidth could not be determined.

See b/329965643

+
+

Utilization may have been capped at 100% as accurate bandwidth could not be determined.

+
diff --git a/frontend/app/components/op_profile/op_details/op_details.ts b/frontend/app/components/op_profile/op_details/op_details.ts index 74ac22991..20a1df79a 100644 --- a/frontend/app/components/op_profile/op_details/op_details.ts +++ b/frontend/app/components/op_profile/op_details/op_details.ts @@ -1,8 +1,9 @@ -import {Component, EventEmitter, Input, Output} from '@angular/core'; +import {Component, EventEmitter, inject, Input, Output} from '@angular/core'; import {Store} from '@ngrx/store'; import {Node} from 'org_xprof/frontend/app/common/interfaces/op_profile.jsonpb_decls'; import {NavigationEvent} from 'org_xprof/frontend/app/common/interfaces/navigation_event'; import * as utils from 'org_xprof/frontend/app/common/utils/utils'; +import {DATA_SERVICE_INTERFACE_TOKEN} from 'org_xprof/frontend/app/services/data_service_v2/data_service_v2_interface'; import {getActiveOpProfileNodeState, getCurrentRun, getOpProfileRootNode, getProfilingGeneralState, getSelectedOpNodeChainState} from 'org_xprof/frontend/app/store/selectors'; import {ProfilingGeneralState} from 'org_xprof/frontend/app/store/state'; import {Observable, ReplaySubject} from 'rxjs'; @@ -18,6 +19,7 @@ import {takeUntil} from 'rxjs/operators'; export class OpDetails { /** Handles on-destroy Subject, used to unsubscribe. */ private readonly destroyed = new ReplaySubject(1); + private readonly dataService = inject(DATA_SERVICE_INTERFACE_TOKEN); /** When updating app route to other tools through crosslink */ @Output() readonly updateRoute = new EventEmitter(); @@ -134,23 +136,14 @@ export class OpDetails { this.moduleList[0]; } - getGraphViewerLink() { - if (this.isOss) { - const tag = 'graph_viewer'; - const host = this.getSelectedModuleName(); - const opName = this.getSelectedOpName(); - return `${window.parent.location.origin}?tool=${tag}&host=${ - host}&opName=${opName}&run=${this.currentRun}#profile`; - } - const aggregatedBy = this.selectedOpNodeChain[0]; - if (aggregatedBy === 'by_program') { - return `/graph_viewer/${this.sessionId}?module_name=${ - this.getSelectedModuleName()}&node_name=${this.getSelectedOpName()}`; - } else if (aggregatedBy === 'by_category') { - return `/graph_viewer/${this.sessionId}?module_name=${ - this.getSelectedModuleName()}&node_name=${this.getSelectedOpName()}`; - } - return ''; + getGraphViewerLinkWrapper() { + const moduleName = this.getSelectedModuleName(); + const opName = this.getSelectedOpName(); + return this.dataService.getGraphViewerLink( + this.sessionId, + moduleName, + opName, + ); } getCustomCallTextLink() { diff --git a/frontend/app/components/op_profile/op_profile.ng.html b/frontend/app/components/op_profile/op_profile.ng.html index 004791958..958cb33bc 100644 --- a/frontend/app/components/op_profile/op_profile.ng.html +++ b/frontend/app/components/op_profile/op_profile.ng.html @@ -1,77 +1,5 @@ -
-
-
- Overall {{deviceType}} FLOPS utilization is - {{data.flopsUtilizationPercent}} -
-
- HBM bandwidth utilization is - {{data.bandwidthUtilizationPercents[data.memBwType.MEM_BW_TYPE_HBM_RW]}} -
-
-
-
- Modifying your model's architecture, data dimensions, and improving - the efficiency of CPU operations may help reach the {{deviceType}}'s FLOPS - potential. -
-
- "Idle" represents the portion of the total execution time on device - that is idle. -
-
-
-
-
Group by Op Category
- -
-
-
- Order by Wasted Time - - info - -
- -
-
-
Top 90% - - info - -
- -
-
-
Exclude Idle
- -
-
- - Ops Limit - - -
-
-
- - - + + +
+
+
diff --git a/frontend/app/components/op_profile/op_profile.scss b/frontend/app/components/op_profile/op_profile.scss deleted file mode 100644 index 93f724d6d..000000000 --- a/frontend/app/components/op_profile/op_profile.scss +++ /dev/null @@ -1,3 +0,0 @@ -/** CSS for an op profile component. */ - -@import 'frontend/app/components/op_profile/op_profile_common'; diff --git a/frontend/app/components/op_profile/op_profile.ts b/frontend/app/components/op_profile/op_profile.ts index 44ecc9257..6d6c219ba 100644 --- a/frontend/app/components/op_profile/op_profile.ts +++ b/frontend/app/components/op_profile/op_profile.ts @@ -1,67 +1,65 @@ import {Component, OnDestroy} from '@angular/core'; -import {ActivatedRoute} from '@angular/router'; +import {ActivatedRoute, Params} from '@angular/router'; import {Store} from '@ngrx/store'; import {OpProfileProto} from 'org_xprof/frontend/app/common/interfaces/data_table'; import {NavigationEvent} from 'org_xprof/frontend/app/common/interfaces/navigation_event'; +import {setLoadingState} from 'org_xprof/frontend/app/common/utils/utils'; import {DataService} from 'org_xprof/frontend/app/services/data_service/data_service'; -import {setLoadingStateAction, setOpProfileRootNodeAction, setProfilingDeviceTypeAction} from 'org_xprof/frontend/app/store/actions'; +import {setProfilingDeviceTypeAction} from 'org_xprof/frontend/app/store/actions'; import {ReplaySubject} from 'rxjs'; import {takeUntil} from 'rxjs/operators'; -import {OpProfileBase} from './op_profile_base'; - /** An op profile component. */ @Component({ standalone: false, selector: 'op-profile', templateUrl: './op_profile.ng.html', - styleUrls: ['./op_profile.scss'] + styleUrls: ['./op_profile_common.scss'] }) -export class OpProfile extends OpProfileBase implements OnDestroy { +export class OpProfile implements OnDestroy { /** Handles on-destroy Subject, used to unsubscribe. */ private readonly destroyed = new ReplaySubject(1); + run = ''; + tag = ''; + host = ''; + opProfileData: OpProfileProto|null = null; + constructor( - route: ActivatedRoute, private readonly dataService: DataService, - private readonly store: Store<{}>) { - super(); + route: ActivatedRoute, + private readonly dataService: DataService, + private readonly store: Store<{}>, + ) { route.params.pipe(takeUntil(this.destroyed)).subscribe((params) => { + this.processQuery(params); this.update(params as NavigationEvent); }); } + processQuery(params: Params) { + this.run = params['run'] || ''; + this.tag = params['tag'] || 'op-profiler'; + this.host = params['host'] || ''; + } + update(event: NavigationEvent) { - this.store.dispatch(setLoadingStateAction({ - loadingState: { - loading: true, - message: 'Loading data', - } - })); + setLoadingState(true, this.store, 'Loading op profile data'); - this.dataService - .getData(event.run || '', event.tag || 'op_profile', event.host || '') + this.dataService.getData(this.run, this.tag, this.host) .pipe(takeUntil(this.destroyed)) .subscribe((data) => { - this.store.dispatch(setLoadingStateAction({ - loadingState: { - loading: false, - message: '', - } - })); + setLoadingState(false, this.store, 'Loading op profile data'); if (data) { - const profileProtoData = data as OpProfileProto; + this.opProfileData = data as OpProfileProto; this.store.dispatch(setProfilingDeviceTypeAction( - {deviceType: profileProtoData.deviceType})); + {deviceType: this.opProfileData.deviceType})); } - this.parseData(data as (OpProfileProto | null)); - this.store.dispatch( - setOpProfileRootNodeAction({rootNode: this.rootNode || null})); }); } ngOnDestroy() { // Unsubscribes all pending subscriptions. - this.store.dispatch(setOpProfileRootNodeAction({rootNode: undefined})); + setLoadingState(false, this.store); this.destroyed.next(); this.destroyed.complete(); } diff --git a/frontend/app/components/op_profile/op_profile_base.ng.html b/frontend/app/components/op_profile/op_profile_base.ng.html new file mode 100644 index 000000000..3df538997 --- /dev/null +++ b/frontend/app/components/op_profile/op_profile_base.ng.html @@ -0,0 +1,85 @@ + + + + + +
+
+
+ Overall {{deviceType}} FLOPS utilization is + {{data.flopsUtilizationPercent}} +
+
+ Memory bandwidth utilizations: + {{metric.name}} {{metric.value}} +
+
+
+
+ Modifying your model's architecture, data dimensions, and improving + the efficiency of CPU operations may help reach the {{deviceType}}'s FLOPS + potential. +
+
+ "IDLE" represents the portion of the total execution time on device + that is idle. +
+
+
+
+
Group by Category
+ +
+
+
+ Order by wasted time + + info + +
+ +
+
+
Top 90% + + info + +
+ +
+
+
Exclude Idle
+ +
+
+ + Ops Limit + + +
+
+
+ + + +
+
diff --git a/frontend/app/components/op_profile/op_profile_base.ts b/frontend/app/components/op_profile/op_profile_base.ts index c1ac56ca8..6435aace6 100644 --- a/frontend/app/components/op_profile/op_profile_base.ts +++ b/frontend/app/components/op_profile/op_profile_base.ts @@ -1,10 +1,26 @@ +import {Component, inject, Input, OnDestroy, SimpleChanges} from '@angular/core'; +import {Params} from '@angular/router'; +import {Store} from '@ngrx/store'; import {Node} from 'org_xprof/frontend/app/common/interfaces/op_profile.jsonpb_decls'; -import {OpProfileProto} from 'org_xprof/frontend/app/common/interfaces/data_table'; +import {type OpProfileProto} from 'org_xprof/frontend/app/common/interfaces/data_table'; +import {NavigationEvent} from 'org_xprof/frontend/app/common/interfaces/navigation_event'; +import {DATA_SERVICE_INTERFACE_TOKEN} from 'org_xprof/frontend/app/services/data_service_v2/data_service_v2_interface'; +import {setCurrentToolStateAction, setOpProfileRootNodeAction} from 'org_xprof/frontend/app/store/actions'; +import {ReplaySubject} from 'rxjs'; -import {OpProfileData} from './op_profile_data'; +import {OpProfileData, OpProfileSummary} from './op_profile_data'; /** Base class of Op Profile component. */ -export class OpProfileBase { +@Component({ + standalone: false, + selector: 'op-profile-base', + templateUrl: './op_profile_base.ng.html', + styleUrls: ['./op_profile_common.scss'] +}) +export class OpProfileBase implements OnDestroy { + /** Handles on-destroy Subject, used to unsubscribe. */ + private readonly destroyed = new ReplaySubject(1); + private readonly dataService = inject(DATA_SERVICE_INTERFACE_TOKEN); profile: OpProfileProto|null = null; rootNode?: Node; data = new OpProfileData(); @@ -15,6 +31,36 @@ export class OpProfileBase { showP90 = false; childrenCount = 10; deviceType = 'TPU'; + summary: OpProfileSummary[] = []; + + @Input() opProfileData: OpProfileProto|null = null; + + processQuery(params: Params) {} + update(event: NavigationEvent) {} + parseData(data: OpProfileProto|null) { + this.profile = data; + this.hasMultiModules = + !!this.profile && !!this.profile.byCategory && !!this.profile.byProgram; + this.isByCategory = false; + this.updateRoot(); + this.data.update(this.rootNode); + this.summary = this.dataService.getOpProfileSummary(this.data); + } + + constructor( + private readonly store: Store<{}>, + ) { + this.store.dispatch( + setCurrentToolStateAction({currentTool: 'hlo_op_profile'}), + ); + } + + ngOnChanges(changes: SimpleChanges) { + if (changes['opProfileData'].previousValue === null && + changes['opProfileData'].currentValue !== null) { + this.parseData(this.opProfileData); + } + } private updateRoot() { if (!this.profile) { @@ -40,18 +86,13 @@ export class OpProfileBase { } this.deviceType = this.profile.deviceType || 'TPU'; + this.store.dispatch( + setOpProfileRootNodeAction({rootNode: this.rootNode}), + ); } - parseData(data: OpProfileProto|null) { - this.profile = data; - this.hasMultiModules = - !!this.profile && !!this.profile.byCategory && !!this.profile.byProgram; - this.isByCategory = false; - this.updateRoot(); - this.data.update(this.rootNode); - } - - updateChildrenCount(value: number) { + updateChildrenCount(event: Event) { + const value = Number((event.target as HTMLInputElement).value); const rounded = Math.round(value / 10) * 10; this.childrenCount = Math.max(Math.min(rounded, 100), 10); @@ -75,4 +116,11 @@ export class OpProfileBase { updateShowP90() { this.showP90 = !this.showP90; } + + ngOnDestroy() { + // Unsubscribes all pending subscriptions. + this.store.dispatch(setOpProfileRootNodeAction({rootNode: undefined})); + this.destroyed.next(); + this.destroyed.complete(); + } } diff --git a/frontend/app/components/op_profile/op_profile_base_module.ts b/frontend/app/components/op_profile/op_profile_base_module.ts new file mode 100644 index 000000000..57e05335f --- /dev/null +++ b/frontend/app/components/op_profile/op_profile_base_module.ts @@ -0,0 +1,29 @@ +import {CommonModule} from '@angular/common'; +import {NgModule} from '@angular/core'; +import {MatFormFieldModule} from '@angular/material/form-field'; +import {MatIconModule} from '@angular/material/icon'; +import {MatInputModule} from '@angular/material/input'; +import {MatSidenavModule} from '@angular/material/sidenav'; +import {MatSlideToggleModule} from '@angular/material/slide-toggle'; +import {MatTooltipModule} from '@angular/material/tooltip'; + +import {OpProfileBase} from './op_profile_base'; +import {OpTableModule} from './op_table/op_table_module'; + +/** An op profile module. */ +@NgModule({ + declarations: [OpProfileBase], + imports: [ + MatFormFieldModule, + MatInputModule, + MatSlideToggleModule, + OpTableModule, + MatIconModule, + MatTooltipModule, + MatSidenavModule, + CommonModule, + ], + exports: [OpProfileBase] +}) +export class OpProfileBaseModule { +} diff --git a/frontend/app/components/op_profile/op_profile_common.scss b/frontend/app/components/op_profile/op_profile_common.scss index f1e181aa3..1f020e898 100644 --- a/frontend/app/components/op_profile/op_profile_common.scss +++ b/frontend/app/components/op_profile/op_profile_common.scss @@ -2,6 +2,16 @@ @import 'frontend/app/styles/common'; +mat-sidenav-container { + background-color: #fff; +} + +mat-sidenav { + background: transparent; + width: 340px; + @include border-right-gray; +} + .container { padding: 20px; } diff --git a/frontend/app/components/op_profile/op_profile_data.ts b/frontend/app/components/op_profile/op_profile_data.ts index 557d3ebed..db6b03862 100644 --- a/frontend/app/components/op_profile/op_profile_data.ts +++ b/frontend/app/components/op_profile/op_profile_data.ts @@ -1,6 +1,13 @@ import {Node} from 'org_xprof/frontend/app/common/interfaces/op_profile.jsonpb_decls'; import * as utils from 'org_xprof/frontend/app/common/utils/utils'; +/** An op profile summary data interface. */ +export interface OpProfileSummary { + name: string; + value: string; + color: string; +} + /** An op profile data class. */ export class OpProfileData { bwColors: string[] = @@ -11,7 +18,6 @@ export class OpProfileData { Array.from({length: utils.MemBwType.MEM_BW_TYPE_MAX + 1}) .fill(''); flopsUtilizationPercent?: string; - memBwType = utils.MemBwType; update(node?: Node) { if (node) { diff --git a/frontend/app/components/op_profile/op_profile_module.ts b/frontend/app/components/op_profile/op_profile_module.ts index c73161f36..a86e4a116 100644 --- a/frontend/app/components/op_profile/op_profile_module.ts +++ b/frontend/app/components/op_profile/op_profile_module.ts @@ -1,23 +1,17 @@ +import {CommonModule} from '@angular/common'; import {NgModule} from '@angular/core'; -import {MatFormFieldModule} from '@angular/material/form-field'; -import {MatIconModule} from '@angular/material/icon'; -import {MatInputModule} from '@angular/material/input'; -import {MatSlideToggleModule} from '@angular/material/slide-toggle'; -import {MatTooltipModule} from '@angular/material/tooltip'; +import {OpDetailsModule} from 'org_xprof/frontend/app/components/op_profile/op_details/op_details_module'; +import {OpProfileBaseModule} from 'org_xprof/frontend/app/components/op_profile/op_profile_base_module'; import {OpProfile} from './op_profile'; -import {OpTableModule} from './op_table/op_table_module'; /** An op profile module. */ @NgModule({ declarations: [OpProfile], imports: [ - MatFormFieldModule, - MatInputModule, - MatSlideToggleModule, - OpTableModule, - MatIconModule, - MatTooltipModule, + OpDetailsModule, + CommonModule, + OpProfileBaseModule, ], exports: [OpProfile] }) diff --git a/frontend/app/components/sidenav/sidenav.ng.html b/frontend/app/components/sidenav/sidenav.ng.html index 0d657bebe..d1ec641d3 100644 --- a/frontend/app/components/sidenav/sidenav.ng.html +++ b/frontend/app/components/sidenav/sidenav.ng.html @@ -48,10 +48,6 @@
-
- -
-
diff --git a/frontend/app/services/data_service_v2/BUILD b/frontend/app/services/data_service_v2/BUILD index be7183d18..70b6a1b23 100644 --- a/frontend/app/services/data_service_v2/BUILD +++ b/frontend/app/services/data_service_v2/BUILD @@ -15,6 +15,8 @@ xprof_ng_module( "@org_xprof//frontend/app/common/angular:angular_common_http", "@org_xprof//frontend/app/common/constants", "@org_xprof//frontend/app/common/interfaces", + "@org_xprof//frontend/app/common/utils", + "@org_xprof//frontend/app/components/op_profile:op_profile_data", "@org_xprof//frontend/app/services/data_service:mock_data", ], ) @@ -28,5 +30,6 @@ xprof_ng_module( "@npm//@angular/core", "@npm//rxjs", "@org_xprof//frontend/app/common/interfaces", + "@org_xprof//frontend/app/components/op_profile:op_profile_data", ], ) diff --git a/frontend/app/services/data_service_v2/data_service_v2.ts b/frontend/app/services/data_service_v2/data_service_v2.ts index c25af88d1..e48d0df2b 100644 --- a/frontend/app/services/data_service_v2/data_service_v2.ts +++ b/frontend/app/services/data_service_v2/data_service_v2.ts @@ -3,6 +3,8 @@ import {HttpClient, HttpParams} from '@angular/common/http'; import {Injectable} from '@angular/core'; import {API_PREFIX, DATA_API, LOCAL_URL, PLUGIN_NAME} from 'org_xprof/frontend/app/common/constants/constants'; import {DataTable} from 'org_xprof/frontend/app/common/interfaces/data_table'; +import * as utils from 'org_xprof/frontend/app/common/utils/utils'; +import {OpProfileData, OpProfileSummary} from 'org_xprof/frontend/app/components/op_profile/op_profile_data'; import {DataServiceV2Interface} from 'org_xprof/frontend/app/services/data_service_v2/data_service_v2_interface'; import {Observable} from 'rxjs'; @@ -37,4 +39,21 @@ export class DataServiceV2 implements DataServiceV2Interface { return this.httpClient.get(this.pathPrefix + DATA_API, {params}) as Observable; } + + getGraphViewerLink(sessionId: string, moduleName: string, opName: string) { + if (!moduleName || !opName) return ''; + return `${window.parent.location.origin}?tool=graph_viewer&host=${ + moduleName}&opName=${opName}&run=${sessionId}#profile`; + } + + getOpProfileSummary(data: OpProfileData): OpProfileSummary[] { + return [ + { + name: 'Hbm', + value: data?.bandwidthUtilizationPercents + ?.[utils.MemBwType.MEM_BW_TYPE_HBM_RW], + color: data?.bwColors?.[utils.MemBwType.MEM_BW_TYPE_HBM_RW], + }, + ]; + } } diff --git a/frontend/app/services/data_service_v2/data_service_v2_interface.ts b/frontend/app/services/data_service_v2/data_service_v2_interface.ts index 8905dab75..82e03bea7 100644 --- a/frontend/app/services/data_service_v2/data_service_v2_interface.ts +++ b/frontend/app/services/data_service_v2/data_service_v2_interface.ts @@ -4,6 +4,7 @@ import {InjectionToken} from '@angular/core'; import {DataTable} from 'org_xprof/frontend/app/common/interfaces/data_table'; +import {OpProfileData, OpProfileSummary} from 'org_xprof/frontend/app/components/op_profile/op_profile_data'; import {Observable} from 'rxjs'; /** The data service class that calls API and return response. */ @@ -15,6 +16,11 @@ export interface DataServiceV2Interface { parameters?: Map, ignoreError?: boolean, ): Observable; + + getGraphViewerLink(sessionId: string, moduleName: string, opName: string): + string; + + getOpProfileSummary(data: OpProfileData): OpProfileSummary[]; } /** Injection token for the data service interface. */