-
Notifications
You must be signed in to change notification settings - Fork 0
/
position.ml
121 lines (92 loc) · 2.13 KB
/
position.ml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
open Lexing
type lexing_position = Lexing.position
type t =
{
start_p : lexing_position;
end_p : lexing_position
} [@@deriving sexp]
type position = t
type 'a located =
{
value : 'a;
position : t;
} [@@deriving sexp]
let value { value ; _ } =
value
let position { position ; _ } =
position
let destruct p =
(p.value, p.position)
let located f x =
f (value x)
let with_pos p v =
{
value = v;
position = p;
}
let with_poss p1 p2 v =
with_pos { start_p = p1; end_p = p2 } v
let map f v =
{
value = f v.value;
position = v.position;
}
let iter f { value; _ } =
f value
let mapd f v =
let w1, w2 = f v.value in
let pos = v.position in
({ value = w1; position = pos }, { value = w2; position = pos })
let dummy =
{
start_p = Lexing.dummy_pos;
end_p = Lexing.dummy_pos
}
let unknown_pos v =
{
value = v;
position = dummy
}
let start_of_position p = p.start_p
let end_of_position p = p.end_p
let filename_of_position p =
p.start_p.Lexing.pos_fname
let line p =
p.pos_lnum
let column p =
p.pos_cnum - p.pos_bol
let characters p1 p2 =
(column p1, p2.pos_cnum - p1.pos_bol) (* intentionally [p1.pos_bol] *)
let join x1 x2 =
{
start_p = if x1 = dummy then x2.start_p else x1.start_p;
end_p = if x2 = dummy then x1.end_p else x2.end_p
}
let lex_join x1 x2 =
{
start_p = x1;
end_p = x2
}
let string_of_lex_pos p =
let c = p.pos_cnum - p.pos_bol in
(string_of_int p.pos_lnum)^":"^(string_of_int c)
let string_of_pos p =
let filename = filename_of_position p in
let l = line p.start_p in
let c1, c2 = characters p.start_p p.end_p in
if filename = "" then
Printf.sprintf "Line %d, characters %d-%d" l c1 c2
else
Printf.sprintf "File \"%s\", line %d, characters %d-%d" filename l c1 c2
let pos_or_undef = function
| None -> dummy
| Some x -> x
let cpos lexbuf =
{
start_p = Lexing.lexeme_start_p lexbuf;
end_p = Lexing.lexeme_end_p lexbuf;
}
let with_cpos lexbuf v =
with_pos (cpos lexbuf) v
let string_of_cpos lexbuf =
string_of_pos (cpos lexbuf)