-
-
Notifications
You must be signed in to change notification settings - Fork 865
Expand file tree
/
Copy pathbound_identifier.rs
More file actions
128 lines (115 loc) · 4.61 KB
/
bound_identifier.rs
File metadata and controls
128 lines (115 loc) · 4.61 KB
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
122
123
124
125
126
127
128
use oxc_ast::{
ast::{BindingIdentifier, BindingPattern, IdentifierReference},
NONE,
};
use oxc_span::{Atom, Span, SPAN};
use oxc_syntax::{reference::ReferenceFlags, symbol::SymbolId};
use crate::TraverseCtx;
/// Info about a binding, from which one can create a `BindingIdentifier` or `IdentifierReference`s.
///
/// Typical usage:
///
/// ```rs
/// // Generate a UID for a top-level var
/// let binding = BoundIdentifier::new_root_uid("foo", SymbolFlags::FunctionScopedVariable, ctx);
///
/// // Generate an `IdentifierReference`s and insert them into AST
/// some_node.id = binding.create_read_reference(ctx);
/// some_other_node.id = binding.create_read_reference(ctx);
///
/// // Store details of the binding for later
/// self.foo_binding = binding;
///
/// // Later on in `exit_program`
/// let id = binding.create_binding_identifier();
/// // Insert `var <id> = something;` into `program.body`
/// ```
///
/// Notes:
///
/// * `BoundIdentifier` is smaller than `BindingIdentifier`, so takes less memory when you store
/// it for later use.
/// * `BoundIdentifier` is `Clone` (unlike `BindingIdentifier`).
/// * `BoundIdentifier` re-uses the same `Atom` for all `BindingIdentifier` / `IdentifierReference`s
/// created from it.
#[derive(Clone)]
pub struct BoundIdentifier<'a> {
pub name: Atom<'a>,
pub symbol_id: SymbolId,
}
impl<'a> BoundIdentifier<'a> {
/// Create `BoundIdentifier` for `name` and `symbol_id`
pub fn new(name: Atom<'a>, symbol_id: SymbolId) -> Self {
Self { name, symbol_id }
}
/// Create `BindingIdentifier` for this binding
pub fn create_binding_identifier(&self) -> BindingIdentifier<'a> {
BindingIdentifier::new_with_symbol_id(SPAN, self.name.clone(), self.symbol_id)
}
/// Create `BindingPattern` for this binding
pub fn create_binding_pattern(&self, ctx: &mut TraverseCtx<'a>) -> BindingPattern<'a> {
let ident = self.create_binding_identifier();
let binding_pattern_kind = ctx.ast.binding_pattern_kind_from_binding_identifier(ident);
ctx.ast.binding_pattern(binding_pattern_kind, NONE, false)
}
/// Create `IdentifierReference` referencing this binding, which is read from, with dummy `Span`
pub fn create_read_reference(&self, ctx: &mut TraverseCtx<'a>) -> IdentifierReference<'a> {
self.create_spanned_read_reference(SPAN, ctx)
}
/// Create `IdentifierReference` referencing this binding, which is read from, with specified `Span`
pub fn create_spanned_read_reference(
&self,
span: Span,
ctx: &mut TraverseCtx<'a>,
) -> IdentifierReference<'a> {
self.create_spanned_reference(span, ReferenceFlags::Read, ctx)
}
/// Create `IdentifierReference` referencing this binding, which is written to, with dummy `Span`
#[allow(unused)]
pub fn create_write_reference(&self, ctx: &mut TraverseCtx<'a>) -> IdentifierReference<'a> {
self.create_spanned_write_reference(SPAN, ctx)
}
/// Create `IdentifierReference` referencing this binding, which is written to, with specified `Span`
pub fn create_spanned_write_reference(
&self,
span: Span,
ctx: &mut TraverseCtx<'a>,
) -> IdentifierReference<'a> {
self.create_spanned_reference(span, ReferenceFlags::Write, ctx)
}
/// Create `IdentifierReference` referencing this binding, which is read from + written to,
/// with dummy `Span`
#[allow(unused)]
pub fn create_read_write_reference(
&self,
ctx: &mut TraverseCtx<'a>,
) -> IdentifierReference<'a> {
self.create_spanned_read_write_reference(SPAN, ctx)
}
/// Create `IdentifierReference` referencing this binding, which is read from + written to,
/// with specified `Span`
pub fn create_spanned_read_write_reference(
&self,
span: Span,
ctx: &mut TraverseCtx<'a>,
) -> IdentifierReference<'a> {
self.create_spanned_reference(span, ReferenceFlags::Read | ReferenceFlags::Write, ctx)
}
/// Create `IdentifierReference` referencing this binding, with specified `ReferenceFlags`
pub fn create_reference(
&self,
flags: ReferenceFlags,
ctx: &mut TraverseCtx<'a>,
) -> IdentifierReference<'a> {
self.create_spanned_reference(SPAN, flags, ctx)
}
/// Create `IdentifierReference` referencing this binding, with specified `Span` and `ReferenceFlags`
pub fn create_spanned_reference(
&self,
span: Span,
flags: ReferenceFlags,
ctx: &mut TraverseCtx<'a>,
) -> IdentifierReference<'a> {
ctx.create_bound_reference_id(span, self.name.clone(), self.symbol_id, flags)
}
}