@@ -65,12 +65,16 @@ func (r Range) Span() (Span, error) {
6565 return Span {}, fmt .Errorf ("file not found in FileSet" )
6666 }
6767 s := Span {v : span {URI : FileURI (f .Name ())}}
68- if ! r .Start .IsValid () {
69- return Span {}, fmt .Errorf ("invalid position for start of range" )
68+ var err error
69+ s .v .Start .Offset , err = offset (f , r .Start )
70+ if err != nil {
71+ return Span {}, err
7072 }
71- s .v .Start .Offset = f .Offset (r .Start )
7273 if r .End .IsValid () {
73- s .v .End .Offset = f .Offset (r .End )
74+ s .v .End .Offset , err = offset (f , r .End )
75+ if err != nil {
76+ return Span {}, err
77+ }
7478 }
7579 s .v .Start .clean ()
7680 s .v .End .clean ()
@@ -79,6 +83,15 @@ func (r Range) Span() (Span, error) {
7983 return s .WithPosition (converter )
8084}
8185
86+ // offset is a copy of the Offset function in go/token, but with the adjustment
87+ // that it does not panic on invalid positions.
88+ func offset (f * token.File , pos token.Pos ) (int , error ) {
89+ if int (pos ) < f .Base () || int (pos ) > f .Base ()+ f .Size () {
90+ return 0 , fmt .Errorf ("invalid pos" )
91+ }
92+ return int (pos ) - f .Base (), nil
93+ }
94+
8295// Range converts a Span to a Range that represents the Span for the supplied
8396// File.
8497func (s Span ) Range (converter * TokenConverter ) (Range , error ) {
@@ -121,5 +134,5 @@ func (l *TokenConverter) ToOffset(line, col int) (int, error) {
121134 // we assume that column is in bytes here, and that the first byte of a
122135 // line is at column 1
123136 pos += token .Pos (col - 1 )
124- return l .file . Offset ( pos ), nil
137+ return offset ( l .file , pos )
125138}
0 commit comments