Fix assignment to qualified statics

ca4687c0f9c797c076b4c42d44aaee56daceb51cf7917894baf32fd242da551b
Alexis Sellier committed ago 1 parent c5ab32c8
lib/std/lang/lower.rad +7 -0
5335 5335
/// Lower an assignment target that designates a memory location, and return
5336 5336
/// the address to store through. Returns `nil` without emitting anything for
5337 5337
/// targets that aren't memory-backed, such as locals tracked in SSA.
5338 5338
unsafe fn lowerPlace(self: &mut FnLowerer, target: *ast::Node) -> ?FieldRef throws (LowerError) {
5339 5339
    match target.value {
5340 +
        case ast::NodeValue::ScopeAccess(_) => {
5341 +
            let sym = try symOf(self, target);
5342 +
            let case resolver::SymbolData::Value { type, .. } = sym.data else {
5343 +
                throw LowerError::ImmutableAssignment;
5344 +
            };
5345 +
            return FieldRef { base: emitDataAddr(self, sym), offset: 0, fieldType: type };
5346 +
        }
5340 5347
        case ast::NodeValue::FieldAccess(access) => {
5341 5348
            return try lowerFieldRef(self, access);
5342 5349
        }
5343 5350
        case ast::NodeValue::Deref(pointer) => {
5344 5351
            // Dereference: `*ptr` or `*r` on a single-field unlabeled record.
test/tests/assign.qualified.static.rad added +15 -0
1 +
//! returns: 0
2 +
3 +
mod storage;
4 +
5 +
@default unsafe fn main() -> u64 {
6 +
    let value = storage::Pair { first: 42, second: 99 };
7 +
    set storage::VALUE = value;
8 +
    assert storage::VALUE.first == 42 and storage::VALUE.second == 99;
9 +
    set storage::COUNT = 7;
10 +
    set storage::COUNT += 5;
11 +
    assert storage::COUNT == 12;
12 +
    set storage::VALUE = storage::Pair { first: 3, second: 4 };
13 +
    assert storage::VALUE.first == 3 and storage::VALUE.second == 4;
14 +
    return 0;
15 +
}
test/tests/assign.qualified.static/storage.rad added +13 -0
1 +
/// Aggregate stored in a qualified static.
2 +
export record Pair: Copy {
3 +
    /// First test value.
4 +
    first: u64,
5 +
    /// Second test value.
6 +
    second: u64,
7 +
}
8 +
9 +
/// Mutable aggregate storage.
10 +
export unsafe static VALUE: Pair = Pair { first: 0, second: 0 };
11 +
12 +
/// Mutable scalar storage.
13 +
export unsafe static COUNT: u64 = 0;