profile
viewpoint

google/pprof-nodejs 96

pprof support for Node.js

wyk9787/G-ChatBox 1

A P2P chat box implemented in C which provides both scalability and fault tolerance.

wyk9787/G-Thread 1

A lock-free software-only runtime system for C++ that eliminates concurrency errors for fork-join parallel programs

wyk9787/MIT-6.828 1

MIT-6.828 Operating System Engineering

wyk9787/ACM-ICPC 0

Solved problems for ICPC

wyk9787/AppDev 0

Learning Objective-C and iOS developing in AppDev Grinnell

wyk9787/Catify 0

An iOS app to help stray cats find their home or help you find your new cat

issue commentGoogleCloudPlatform/cloud-profiler-python

Failed to collect and upload profile: dictionary changed size during iteration

this is a fastapi application.

tool.poetry.dependencies]
python = "^3.7"
fastapi = "^0.61.0"
httpx = { extras = ["http2"], version = "^0.16.1" }
uvicorn = "^0.11.8"
loguru = "^0.5.1"
pydantic = {extras = ["email", "dotenv"], version = "^1.7.3"}
pybase62 = "^0.4.3"
arrow = "^0.15.8"
autoname = "^0.1.1"
sentry-sdk = "^0.16.5"
google-api-python-client = "^1.8.4"
google-auth-httplib2 = "^0.0.4"
google-auth-oauthlib = "^0.4.1"
grpcio = "^1.31.0"
motor = "^2.3.0"
dnspython = "^2.0.0"
line-bot-sdk = "^1.18.0"
tenacity = "^6.3.1"
notifiers = "^1.2.1"
omise = "^0.9.0"
python-multipart = "^0.0.5"
furl = "^2.1.0"
imagekitio = "^2.2.5"
jingdi = "^0.1.0"
pyzbar-x = "^0.2.1"
Pillow = "^8.1.0"
fastapi-utils = "^0.2.1"
google-python-cloud-debugger = "^2.15"
tomlkit = "^0.7.0"
locate = "^0.0.1"
parse-with-dot-access = "^1.18.0"
CircleOnCircles

comment created time in 11 hours

issue commentGoogleCloudPlatform/cloud-profiler-python

BlockingIOError on App Engine after some time

@mgrdcm This is not specific to gunicorn, any package or user code could set the same. I appreciate your point regarding App Engine. We will post an update if we figure out a way to address this.

drazzib

comment created time in a day

Pull request review commentgoogle/pprof

Update the function comment for FindProgHeaderForMapping.

 func FindTextProgHeader(f *elf.File) *elf.ProgHeader {  // FindProgHeaderForMapping returns the loadable program segment header that is // fully contained in the runtime mapping with file offset pgoff and memory size-// memsz, or an error if the segment cannot be determined.+// memsz, or an error if the segment cannot be determined. The function returns+// a nil progran header and no error if the ELF binary has no loadable segments.

Oops, updated.

gmarin13

comment created time in a day

Pull request review commentgoogle/pprof

Update the function comment for FindProgHeaderForMapping.

 func FindTextProgHeader(f *elf.File) *elf.ProgHeader {  // FindProgHeaderForMapping returns the loadable program segment header that is // fully contained in the runtime mapping with file offset pgoff and memory size-// memsz, or an error if the segment cannot be determined.+// memsz, or an error if the segment cannot be determined. The function returns+// a nil progran header and no error if the ELF binary has no loadable segments.

typo: progran

gmarin13

comment created time in a day

PR opened google/pprof

Update the function comment for FindProgHeaderForMapping.

Added text to specify that it can return a nil program header in some cases.

+2 -1

0 comment

1 changed file

pr created time in a day

issue openedgoogle/pprof

Source listing not found in webview while present in command line

What version of pprof are you using? GOARCH="amd64" GOBIN="" GOCACHE="/home/USER/.cache/go-build" GOEXE="" GOFLAGS="" GOHOSTARCH="amd64" GOHOSTOS="linux" GOOS="linux" GOPATH="/home/USER/go" GOPROXY="" GORACE="" GOROOT="/home/USER/opt/go" GOTMPDIR="" GOTOOLDIR="/home/USER/opt/go/pkg/tool/linux_amd64" GCCGO="gccgo" CC="gcc" CXX="g++" CGO_ENABLED="1" GOMOD="" CGO_CFLAGS="-g -O2" CGO_CPPFLAGS="" CGO_CXXFLAGS="-g -O2" CGO_FFLAGS="-g -O2" CGO_LDFLAGS="-g -O2" PKG_CONFIG="pkg-config" GOGCCFLAGS="-fPIC -m64 -pthread -fmessage-length=0 -fdebug-prefix-map=/tmp/go-build584220800=/tmp/go-build -gno-record-gcc-switches"

What operating system and processor architecture are you using? Linux Ubuntu 18.04 x64

What did you do? go tool pprof -http=":8000" -source_path=/home/USER/code/APP/src APP cpuProfile.pprof Open the source view, give it focus on "FUNCTION"

FUNCTION_PATH bufio/bufio.go Total: 0 680ms (flat, cum) 3.39% 48 . . ??? 49 . 680ms ??? 55 . . ??? 56 . . ??? 75 . . ??? 78 . . ??? 79 . . ??? --> no source code visible

go tool pprof -source_path=/home/USER/code/APP/src APP cpuProfile.pprof (pprof) list FUNCTION Total: 20.07s ROUTINE ======================== FUNCTION_PATH in bufio/bufio.go 0 680ms (flat, cum) 3.39% of Total Error: Could not find file bufio/bufio.go on path /home/USER/code/APP/src ROUTINE ======================== FUNCTIONPATH in FUNCTION_GO_FILE_IN_GIVEN_PATH.go --> starts listing source code here.

It seems that the webview doesn't show/find the source code, while the command line does.

created time in a day

push eventgoogle/pprof

gmarin13

commit sha 1f0ca0a18a6c71389147d82349e7519e9d270707

Enable symbolization of data objects with the llvm symbolizer (#598) * Compute the correct base offset for non-executable runtime mappings. For user space executables, find the segment associated with the current mapping and use its header in the call to GetBase, instead of using the program header for the segment that includes the .text section. This change is needed for all local symbolizers that handle ELF files. * Enable the llvn-symbolizer to symbolize data addresses. For data addresses, we need to issue "DATA <binary_name> <address>" commands, while for code addresses, we issue "CODE <binary_name> <address>" commands. Right now, the frames for data addresses include the symbol start address and size in the filename field.

view details

push time in 2 days

PR merged google/pprof

Enable symbolization of data objects with the llvm symbolizer cla: yes

This PR adds support for symbolizing virtual data addresses with the llvm-symbolizer. As a prerequisite, we have to compute the correct GetBase offset for data mappings, regardless of which local symbolizer is used.

One of the commits, changes the current behavior from always computing a base offset relative to the executable program segment, to an approach that tries to identify the program segment associated with a given mapping and computing the offset relative to that segment. This change is enabled only for user space mappings. For kernel mappings, we continue to look for the kernel executable segment.

With this change, we drop support for fake mappings that span the entire address space. From an offline discussion with aalexand@:

  • fake mappings were added by https://github.com/google/pprof/pull/89 to handle profiles with no mappings that would be generated by golang runtime sometimes;
  • local experiments by aalexand@ show the fake mapping is present in Go 1.7 heap profiles, but not in Go 1.8 profiles. This may be related to the fact that the older Go versions didn't use profile.proto and generated legacy text format instead;
  • Go 1.7 is not a supported version anymore, so we are OK with dropping support for the fake mapping.
+299 -34

1 comment

6 changed files

gmarin13

pr closed time in 2 days

issue commentGoogleCloudPlatform/cloud-profiler-python

Failed to collect and upload profile: dictionary changed size during iteration

@CircleOnCircles I assume there wasn't a stack?

CircleOnCircles

comment created time in 2 days

pull request commentgoogle/pprof

Revamp how source listing is produced so it works for inlined functions.

Codecov Report

Merging #599 (10d04a0) into master (39141e7) will decrease coverage by 0.48%. The diff coverage is 77.61%.

Impacted file tree graph

@@            Coverage Diff             @@
##           master     #599      +/-   ##
==========================================
- Coverage   66.97%   66.49%   -0.49%     
==========================================
  Files          78       78              
  Lines       14160    14462     +302     
==========================================
+ Hits         9484     9616     +132     
- Misses       3842     3996     +154     
- Partials      834      850      +16     
Impacted Files Coverage Δ
internal/report/source.go 78.86% <77.18%> (-2.55%) :arrow_down:
internal/driver/driver.go 70.39% <100.00%> (+0.67%) :arrow_up:
internal/report/report.go 21.93% <0.00%> (-7.32%) :arrow_down:
.../github.com/google/pprof/internal/report/report.go 21.93% <0.00%> (-7.32%) :arrow_down:
.../github.com/google/pprof/internal/report/source.go 78.86% <0.00%> (-2.55%) :arrow_down:
.../github.com/google/pprof/internal/driver/driver.go 70.39% <0.00%> (+0.67%) :arrow_up:

Continue to review full report at Codecov.

Legend - Click here to learn more Δ = absolute <relative> (impact), ø = not affected, ? = missing data Powered by Codecov. Last update 39141e7...7cd4f88. Read the comment docs.

ghemawat

comment created time in 2 days

PR opened google/pprof

Revamp how source listing is produced so it works for inlined functions.

Some other things improved due to these changes:

  1. Produced output does not contain long runs of uninteresting source.
  2. Speed of producing weblist page for a large binary goes from ~ 57s to ~ 5.5s.
+641 -218

0 comment

8 changed files

pr created time in 2 days

issue openedGoogleCloudPlatform/cloud-profiler-python

Failed to collect and upload profile: dictionary changed size during iteration

this is the bug raised in production capture by sentry.

"Failed to collect and upload profile: dictionary changed size during iteration"

CPython, 3.8.2(3.8.2 (default, Apr 23 2020, 14:22:33) [GCC 8.3.0])

created time in 3 days

startedyamamushi/dumap

started time in 3 days

pull request commentgoogle/pprof

Enable symbolization of data objects with the llvm symbolizer

Codecov Report

Merging #598 (149e940) into master (39141e7) will increase coverage by 0.09%. The diff coverage is 82.05%.

Impacted file tree graph

@@            Coverage Diff             @@
##           master     #598      +/-   ##
==========================================
+ Coverage   66.97%   67.06%   +0.09%     
==========================================
  Files          78       78              
  Lines       14160    14224      +64     
==========================================
+ Hits         9484     9540      +56     
- Misses       3842     3848       +6     
- Partials      834      836       +2     
Impacted Files Coverage Δ
internal/elfexec/elfexec.go 38.09% <80.95%> (+8.57%) :arrow_up:
internal/binutils/addr2liner_llvm.go 65.62% <83.33%> (+1.69%) :arrow_up:
internal/binutils/binutils.go 54.86% <83.33%> (+1.45%) :arrow_up:
.../google/pprof/internal/binutils/addr2liner_llvm.go 71.87% <0.00%> (+1.38%) :arrow_up:
...hub.com/google/pprof/internal/binutils/binutils.go 45.52% <0.00%> (+1.75%) :arrow_up:
...ithub.com/google/pprof/internal/elfexec/elfexec.go 38.09% <0.00%> (+8.57%) :arrow_up:

Continue to review full report at Codecov.

Legend - Click here to learn more Δ = absolute <relative> (impact), ø = not affected, ? = missing data Powered by Codecov. Last update 39141e7...149e940. Read the comment docs.

gmarin13

comment created time in 6 days

pull request commentgoogle/pprof

Enable symbolization of data objects with the llvm symbolizer

Tests failed. Please mark this as draft until it's ready for review.

gmarin13

comment created time in 6 days

PR opened google/pprof

Enable symbolization of data objects with the llvm symbolizer
+295 -138

0 comment

6 changed files

pr created time in 6 days

push eventgoogle/pprof

Stephan Renatus

commit sha 39141e76b6471416fad93e101d512dedec969596

proto/profile.proto: fix typo (#577) Signed-off-by: Stephan Renatus <stephan@styra.com> Co-authored-by: Maggie Nolan <nolanmar@google.com> Co-authored-by: Kalyana Chadalavada <kalyanac@users.noreply.github.com>

view details

push time in 6 days

PR merged google/pprof

proto/profile.proto: fix typo cla: yes
+1 -1

20 comments

1 changed file

srenatus

pr closed time in 6 days

pull request commentgoogle/pprof

proto/profile.proto: fix typo

Fiiinaaaalllly 🎉

srenatus

comment created time in 6 days

pull request commentgoogle/pprof

proto/profile.proto: fix typo

@googlebot I signed it!

srenatus

comment created time in 6 days

startedgoogle-research-datasets/paws

started time in 7 days

pull request commentgoogle/pprof

Add GCUs as a unit type

PTAL

nolanmar511

comment created time in 7 days

Pull request review commentgoogle/pprof

Add GCUs as a unit type

 func timeLabel(value int64, fromUnit, toUnit string) (v float64, u string, ok bo 		toUnit = strings.TrimSuffix(toUnit, "s") 	} -	var d time.Duration-	switch fromUnit {-	case "nanosecond", "ns":-		d = time.Duration(value) * time.Nanosecond-	case "microsecond":-		d = time.Duration(value) * time.Microsecond-	case "millisecond", "ms":-		d = time.Duration(value) * time.Millisecond-	case "second", "sec", "s":-		d = time.Duration(value) * time.Second-	case "cycle":+	if fromUnit == "cycle" { 		return float64(value), "", true-	default:+	}++	uf := func(unit string) (string, float64, bool) {+		return unitFactor(unit, timeUnits)+	}+	as := func(value float64) (float64, string, bool) {+		return autoScale(value, timeUnits)+	}+	return convertUnit(value, fromUnit, toUnit, unit{"s", []string{}, float64(time.Second)}, uf, as)+}++var gcuUnits = []unit{+	{"n*GCU", []string{"nanogcu"}, 1e-9},+	{"u*GCU", []string{"microgcu"}, 1e-6},+	{"m*GCU", []string{"milligcu"}, 1e-3},+	{"GCU", []string{"gcu"}, 1},+	{"k*GCU", []string{"kilogcu"}, 1e3},+	{"M*GCU", []string{"megagcu"}, 1e6},+	{"G*GCU", []string{"gigagcu"}, 1e9},+	{"T*GCU", []string{"teragcu"}, 1e12},+	{"P*GCU", []string{"petagcu"}, 1e15},+}++// isGCUUnit returns whether a name is recognized as a GCU unit.+func isGCUUnit(unit string) bool {+	_, _, gcuUnit := unitFactor(strings.TrimSuffix(strings.ToLower(unit), "s"), gcuUnits)+	return gcuUnit+}++func gcuLabel(value int64, fromUnit, toUnit string) (v float64, u string, ok bool) {+	fromUnit = strings.TrimSuffix(strings.ToLower(fromUnit), "s")+	toUnit = strings.TrimSuffix(strings.ToLower(toUnit), "s")+	uf := func(unit string) (string, float64, bool) {+		return unitFactor(unit, gcuUnits)+	}+	as := func(value float64) (float64, string, bool) {+		return autoScale(value, gcuUnits)+	}+	return convertUnit(value, fromUnit, toUnit, unit{"GCU", []string{}, 1.0}, uf, as)+}++// convertUnit converts a value from the fromUnit to the toUnit, autoscaling+// the value if the toUnit is "minimum" or "auto". If the fromUnit is not+// included in units, then a false boolean will be returned. If the toUnit+// is not in units, the value will be returned in terms of the default unit.+func convertUnit(value int64, fromUnit, toUnit string, defaultUnit unit, unitFactor func(string) (string, float64, bool), autoScale func(float64) (float64, string, bool)) (v float64, u string, ok bool) {+	_, fromUnitFactor, ok := unitFactor(fromUnit)+	if !ok { 		return 0, "", false 	} +	v = float64(value) * fromUnitFactor+ 	if toUnit == "minimum" || toUnit == "auto" {-		switch {-		case d < 1*time.Microsecond:-			toUnit = "ns"-		case d < 1*time.Millisecond:-			toUnit = "us"-		case d < 1*time.Second:-			toUnit = "ms"-		case d < 1*time.Minute:-			toUnit = "sec"-		case d < 1*time.Hour:-			toUnit = "min"-		case d < 24*time.Hour:-			toUnit = "hour"-		case d < 15*24*time.Hour:-			toUnit = "day"-		case d < 120*24*time.Hour:-			toUnit = "week"-		default:-			toUnit = "year"+		if v, u, ok := autoScale(v); ok {+			return v, u, true 		}+		return v / defaultUnit.factor, defaultUnit.canonicalName, true 	} -	var output float64-	dd := float64(d)-	switch toUnit {-	case "ns", "nanosecond":-		output, toUnit = dd/float64(time.Nanosecond), "ns"-	case "us", "microsecond":-		output, toUnit = dd/float64(time.Microsecond), "us"-	case "ms", "millisecond":-		output, toUnit = dd/float64(time.Millisecond), "ms"-	case "min", "minute":-		output, toUnit = dd/float64(time.Minute), "mins"-	case "hour", "hr":-		output, toUnit = dd/float64(time.Hour), "hrs"-	case "day":-		output, toUnit = dd/float64(24*time.Hour), "days"-	case "week", "wk":-		output, toUnit = dd/float64(7*24*time.Hour), "wks"-	case "year", "yr":-		output, toUnit = dd/float64(365*24*time.Hour), "yrs"-	default:-		// "sec", "second", "s" handled by default case.-		output, toUnit = dd/float64(time.Second), "s"+	toUnit, toUnitFactor, ok := unitFactor(toUnit)+	if !ok {+		return v / defaultUnit.factor, defaultUnit.canonicalName, true+	}+	return v / toUnitFactor, toUnit, true+}++// unitFactor returns the canonical name for the unit, the factor by which one+// must multiply a value specified in terms of unit in order to get the value+// specified in terms of the base unit, and a boolean to indicated if a unit+// was identified for the specified unit within the slice units.+func unitFactor(unit string, units []unit) (string, float64, bool) {

Thanks! This is much simpler.

One thing that happened with this change: 'cycle' is no longer treated as a time unit. There weren't any tests which failed because of this, but wanted to call it out in case this could be a problem.

nolanmar511

comment created time in 7 days

Pull request review commentgoogle/pprof

Add GCUs as a unit type

 func timeLabel(value int64, fromUnit, toUnit string) (v float64, u string, ok bo 		toUnit = strings.TrimSuffix(toUnit, "s") 	} -	var d time.Duration-	switch fromUnit {-	case "nanosecond", "ns":-		d = time.Duration(value) * time.Nanosecond-	case "microsecond":-		d = time.Duration(value) * time.Microsecond-	case "millisecond", "ms":-		d = time.Duration(value) * time.Millisecond-	case "second", "sec", "s":-		d = time.Duration(value) * time.Second-	case "cycle":+	if fromUnit == "cycle" { 		return float64(value), "", true-	default:+	}++	uf := func(unit string) (string, float64, bool) {+		return unitFactor(unit, timeUnits)+	}+	as := func(value float64) (float64, string, bool) {+		return autoScale(value, timeUnits)+	}+	return convertUnit(value, fromUnit, toUnit, unit{"s", []string{}, float64(time.Second)}, uf, as)+}++var gcuUnits = []unit{+	{"n*GCU", []string{"nanogcu"}, 1e-9},+	{"u*GCU", []string{"microgcu"}, 1e-6},+	{"m*GCU", []string{"milligcu"}, 1e-3},+	{"GCU", []string{"gcu"}, 1},+	{"k*GCU", []string{"kilogcu"}, 1e3},+	{"M*GCU", []string{"megagcu"}, 1e6},+	{"G*GCU", []string{"gigagcu"}, 1e9},+	{"T*GCU", []string{"teragcu"}, 1e12},+	{"P*GCU", []string{"petagcu"}, 1e15},+}++// isGCUUnit returns whether a name is recognized as a GCU unit.+func isGCUUnit(unit string) bool {+	_, _, gcuUnit := unitFactor(strings.TrimSuffix(strings.ToLower(unit), "s"), gcuUnits)+	return gcuUnit+}++func gcuLabel(value int64, fromUnit, toUnit string) (v float64, u string, ok bool) {+	fromUnit = strings.TrimSuffix(strings.ToLower(fromUnit), "s")+	toUnit = strings.TrimSuffix(strings.ToLower(toUnit), "s")+	uf := func(unit string) (string, float64, bool) {+		return unitFactor(unit, gcuUnits)+	}+	as := func(value float64) (float64, string, bool) {+		return autoScale(value, gcuUnits)+	}+	return convertUnit(value, fromUnit, toUnit, unit{"GCU", []string{}, 1.0}, uf, as)+}++// convertUnit converts a value from the fromUnit to the toUnit, autoscaling+// the value if the toUnit is "minimum" or "auto". If the fromUnit is not+// included in units, then a false boolean will be returned. If the toUnit+// is not in units, the value will be returned in terms of the default unit.+func convertUnit(value int64, fromUnit, toUnit string, defaultUnit unit, unitFactor func(string) (string, float64, bool), autoScale func(float64) (float64, string, bool)) (v float64, u string, ok bool) {+	_, fromUnitFactor, ok := unitFactor(fromUnit)+	if !ok { 		return 0, "", false 	} +	v = float64(value) * fromUnitFactor+ 	if toUnit == "minimum" || toUnit == "auto" {-		switch {-		case d < 1*time.Microsecond:-			toUnit = "ns"-		case d < 1*time.Millisecond:-			toUnit = "us"-		case d < 1*time.Second:-			toUnit = "ms"-		case d < 1*time.Minute:-			toUnit = "sec"-		case d < 1*time.Hour:-			toUnit = "min"-		case d < 24*time.Hour:-			toUnit = "hour"-		case d < 15*24*time.Hour:-			toUnit = "day"-		case d < 120*24*time.Hour:-			toUnit = "week"-		default:-			toUnit = "year"+		if v, u, ok := autoScale(v); ok {+			return v, u, true 		}+		return v / defaultUnit.factor, defaultUnit.canonicalName, true 	} -	var output float64-	dd := float64(d)-	switch toUnit {-	case "ns", "nanosecond":-		output, toUnit = dd/float64(time.Nanosecond), "ns"-	case "us", "microsecond":-		output, toUnit = dd/float64(time.Microsecond), "us"-	case "ms", "millisecond":-		output, toUnit = dd/float64(time.Millisecond), "ms"-	case "min", "minute":-		output, toUnit = dd/float64(time.Minute), "mins"-	case "hour", "hr":-		output, toUnit = dd/float64(time.Hour), "hrs"-	case "day":-		output, toUnit = dd/float64(24*time.Hour), "days"-	case "week", "wk":-		output, toUnit = dd/float64(7*24*time.Hour), "wks"-	case "year", "yr":-		output, toUnit = dd/float64(365*24*time.Hour), "yrs"-	default:-		// "sec", "second", "s" handled by default case.-		output, toUnit = dd/float64(time.Second), "s"+	toUnit, toUnitFactor, ok := unitFactor(toUnit)+	if !ok {+		return v / defaultUnit.factor, defaultUnit.canonicalName, true+	}+	return v / toUnitFactor, toUnit, true+}++// unitFactor returns the canonical name for the unit, the factor by which one+// must multiply a value specified in terms of unit in order to get the value+// specified in terms of the base unit, and a boolean to indicated if a unit+// was identified for the specified unit within the slice units.+func unitFactor(unit string, units []unit) (string, float64, bool) {

This is optional, but I would consider a couple of things API-wise, see WDYT.

We could make []unit a type so that it can be a receiver. I'd also name unitFactor as findByAlias and return *unit from it - the reason is that it returns more than just the factor, it pretty much searches for a unit by alias.

Having a knownUnit function could simplify isTimeUnit / isMemoryUnit / isGCUUnit a bit.

So, something like:

type unitList []unit
...
// findByAlias .... Returns nil if the unit with such alias is not found.
func (us unitList) findByAlias(alias string) *unit {
  ...
}

func (us unitList) autoScale(...) ... {
  ...
}

func (us unitList) sniffUnit(unit string) *unit {
  return us.findByAlias(strings.TrimSuffix(strings.ToLower(unit), "s"))
}

With this, I think you could remove isTimeUnit and its friends as it simply becomes if timeUnits.sniffUnit(s) != nil.

I think convertUnit would also simplify, since now it can also accept a receiver and it doesn't need to accept the function pointers. I could be wrong on this, but I feel that this can simplify.

nolanmar511

comment created time in 8 days

Pull request review commentgoogle/pprof

Add GCUs as a unit type

 func timeLabel(value int64, fromUnit, toUnit string) (v float64, u string, ok bo 		toUnit = strings.TrimSuffix(toUnit, "s") 	} -	var d time.Duration-	switch fromUnit {-	case "nanosecond", "ns":-		d = time.Duration(value) * time.Nanosecond-	case "microsecond":-		d = time.Duration(value) * time.Microsecond-	case "millisecond", "ms":-		d = time.Duration(value) * time.Millisecond-	case "second", "sec", "s":-		d = time.Duration(value) * time.Second-	case "cycle":+	if fromUnit == "cycle" { 		return float64(value), "", true-	default:+	}++	uf := func(unit string) (string, float64, bool) {+		return unitFactor(unit, timeUnits)+	}+	as := func(value float64) (float64, string, bool) {+		return autoScale(value, timeUnits)+	}+	return convertUnit(value, fromUnit, toUnit, unit{"s", []string{}, float64(time.Second)}, uf, as)+}++var caseInsensitiveGCUUnits = []unit{+	{"n*GCU", []string{"nanogcu"}, 1e-9},+	{"u*GCU", []string{"microgcu"}, 1e-6},+	{"m*GCU", []string{"milligcu"}, 1e-3},+	{"GCU", []string{"gcu"}, 1},+	{"k*GCU", []string{"kilogcu"}, 1e3},+	{"M*GCU", []string{"megagcu"}, 1e6},+	{"G*GCU", []string{"gigagcu"}, 1e9},+	{"T*GCU", []string{"teragcu"}, 1e12},+	{"P*GCU", []string{"petagcu"}, 1e15},+}++var caseSensitiveGCUUnits = []unit{

Removed this.

nolanmar511

comment created time in 8 days

PR closed google/pprof

Stop using math.Round to allow for pprof import cla: yes

When @wyk9787 was importing pprof code from here into our internal repository, a test failed with the error undefined: math.Round.

This change removes the usage of math.Round to allow for import of pprof (I manually applied this change while importing pprof and tests built and passed).

I'm open to other fixes; just want to be sure we unblock importing pprof.

+11 -4

2 comments

1 changed file

nolanmar511

pr closed time in 8 days

pull request commentgoogle/pprof

Stop using math.Round to allow for pprof import

There is offline discussion on this, let's resolve that first. It's unclear that supporting pre-1.10 go versions is something we want to do.

nolanmar511

comment created time in 8 days

pull request commentgoogle/pprof

Stop using math.Round to allow for pprof import

It would be nice to understand why this happened - is this Go version incompatibility or what? I'd be surprised if math.Round is particularly new.

nolanmar511

comment created time in 8 days

more