Remove use of `extern` keyword

bfa128abb665d66b2b9a5a7fc564a4d5fc643af59bd527799b6edbe1c7f9cb93
Alexis Sellier committed ago 1 parent 04bdcb9f
lib/std/intrinsics.rad +2 -2
3 3
/// Environment call.
4 4
///
5 5
/// Issues a system call with the given number and arguments.
6 6
/// Arguments and the return value are `i64` to support both 32-bit
7 7
/// emulator addresses and 64-bit native (AMD64) pointers.
8 -
@intrinsic pub extern fn ecall(number: u32, arg1: i64, arg2: i64, arg3: i64, arg4: i64) -> i64;
8 +
@intrinsic pub fn ecall(number: u32, arg1: i64, arg2: i64, arg3: i64, arg4: i64) -> i64;
9 9
10 10
/// Break out of program.
11 -
@intrinsic pub extern fn ebreak();
11 +
@intrinsic pub fn ebreak();
lib/std/lang/parser.rad +0 -4
878 878
    }
879 879
    if consume(p, scanner::TokenKind::Pub) or consume(p, scanner::TokenKind::Export) {
880 880
        let attrNode = nodeAttribute(p, ast::Attribute::Pub);
881 881
        attrs.append(attrNode, p.allocator);
882 882
    }
883 -
    if consume(p, scanner::TokenKind::Extern) {
884 -
        let attrNode = nodeAttribute(p, ast::Attribute::Extern);
885 -
        attrs.append(attrNode, p.allocator);
886 -
    }
887 883
    if attrs.len > 0 {
888 884
        return ast::Attributes { list: attrs };
889 885
    }
890 886
    return nil;
891 887
}
lib/std/lang/parser/tests.rad +3 -13
1115 1115
    try testing::expect(super::check(&parser, scanner::TokenKind::Ident));
1116 1116
}
1117 1117
1118 1118
/// Test parsing a function declaration with attributes.
1119 1119
@test fn testParseFnDeclAttributes() throws (testing::TestError) {
1120 -
    let node = try! parseStmtStr("pub extern fn run();");
1120 +
    let node = try! parseStmtStr("pub fn run();");
1121 1121
    let case ast::NodeValue::FnDecl(decl) = node.value
1122 1122
        else throw testing::TestError::Failed;
1123 1123
1124 1124
    try expectIdent(decl.name, "run");
1125 1125
1139 1139
    try testing::expect(ast::attributesContains(&attrs, ast::Attribute::Pub));
1140 1140
    try testing::expect(ast::attributesContains(&attrs, ast::Attribute::Extern));
1141 1141
    try testing::expect(decl.body == nil);
1142 1142
}
1143 1143
1144 -
@test fn testParseFnDeclAttributesExplicitExternKeepsTwoAttrs() throws (testing::TestError) {
1145 -
    let node = try! parseStmtStr("pub extern fn explicit();");
1146 -
    let case ast::NodeValue::FnDecl(decl) = node.value
1147 -
        else throw testing::TestError::Failed;
1148 -
1149 -
    let attrs = decl.attrs
1150 -
        else throw testing::TestError::Failed;
1151 -
    try testing::expect(attrs.list.len == 2);
1152 -
}
1153 -
1154 -
/// Test parsing a top-level function declaration with inferred extern.
1144 +
/// Test parsing a top-level function declaration with inferred extern from `;`.
1155 1145
@test fn testParseFnDeclInferredExtern() throws (testing::TestError) {
1156 1146
    let node = try! parseStmtStr("fn run();");
1157 1147
    let case ast::NodeValue::FnDecl(decl) = node.value
1158 1148
        else throw testing::TestError::Failed;
1159 1149
1170 1160
1171 1161
    try testing::expect(ast::attributesContains(&attrs, ast::Attribute::Extern));
1172 1162
    try testing::expect(decl.body == nil);
1173 1163
}
1174 1164
1175 -
/// Test parsing a top-level exported function declaration with inferred extern.
1165 +
/// Test parsing a top-level exported function declaration with inferred extern from `;`.
1176 1166
@test fn testParseFnDeclExportInferredExtern() throws (testing::TestError) {
1177 1167
    let node = try! parseStmtStr("export fn run();");
1178 1168
    let case ast::NodeValue::FnDecl(decl) = node.value
1179 1169
        else throw testing::TestError::Failed;
1180 1170
lib/std/lang/resolver.rad +5 -5
498 498
    FnMissingReturn,
499 499
    /// Function is missing a body.
500 500
    FnMissingBody,
501 501
    /// Function body is not expected.
502 502
    FnUnexpectedBody,
503 -
    /// Intrinsic function must be declared extern.
504 -
    IntrinsicRequiresExtern,
503 +
    /// Intrinsic function must not have a body.
504 +
    IntrinsicUnexpectedBody,
505 505
    /// Encountered loop control outside of a loop construct.
506 506
    InvalidLoopControl,
507 507
    /// `try` used when the enclosing function does not declare throws.
508 508
    TryRequiresThrows,
509 509
    /// `try` used to propagate an error not declared by the enclosing function.
3082 3082
    };
3083 3083
    let retTy = *fnType.returnType;
3084 3084
    let isExtern = ast::hasAttribute(sym.attrs, ast::Attribute::Extern);
3085 3085
    let isIntrinsic = ast::hasAttribute(sym.attrs, ast::Attribute::Intrinsic);
3086 3086
3087 -
    if isIntrinsic and not isExtern {
3088 -
        throw emitError(self, node, ErrorKind::IntrinsicRequiresExtern);
3089 -
    }
3090 3087
    if let body = decl.body {
3088 +
        if isIntrinsic {
3089 +
            throw emitError(self, node, ErrorKind::IntrinsicUnexpectedBody);
3090 +
        }
3091 3091
        if isExtern {
3092 3092
            throw emitError(self, node, ErrorKind::FnUnexpectedBody);
3093 3093
        }
3094 3094
        enterFn(self, node, fnType); // Enter function scope for body analysis.
3095 3095
lib/std/lang/resolver/printer.rad +2 -2
407 407
            io::print("function is missing a body");
408 408
        }
409 409
        case super::ErrorKind::FnUnexpectedBody => {
410 410
            io::print("function body is not expected");
411 411
        }
412 -
        case super::ErrorKind::IntrinsicRequiresExtern => {
413 -
            io::print("intrinsic function must be declared extern");
412 +
        case super::ErrorKind::IntrinsicUnexpectedBody => {
413 +
            io::print("intrinsic function must not have a body");
414 414
        }
415 415
        case super::ErrorKind::InvalidLoopControl => {
416 416
            io::print("loop control outside of a loop construct");
417 417
        }
418 418
        case super::ErrorKind::TryRequiresThrows => {
lib/std/lang/scanner.rad +2 -3
95 95
96 96
    // Module-related tokens.
97 97
    Mod, Use, Super,
98 98
99 99
    // Type or function attributes.
100 -
    Pub, Export, Extern, Static,
100 +
    Pub, Export, Static,
101 101
102 102
    // Trait-related tokens.
103 103
    Trait, Instance,
104 104
105 105
    // Type-related tokens.
114 114
    /// Corresponding token.
115 115
    tok: TokenKind,
116 116
}
117 117
118 118
/// Sorted keyword table for binary search.
119 -
const KEYWORDS: [Keyword; 53] = [
119 +
const KEYWORDS: [Keyword; 52] = [
120 120
    { name: "align", tok: TokenKind::Align },
121 121
    { name: "and", tok: TokenKind::And },
122 122
    { name: "as", tok: TokenKind::As },
123 123
    { name: "assert", tok: TokenKind::Assert },
124 124
    { name: "bool", tok: TokenKind::Bool },
128 128
    { name: "const", tok: TokenKind::Const },
129 129
    { name: "constant", tok: TokenKind::Const },
130 130
    { name: "continue", tok: TokenKind::Continue },
131 131
    { name: "else", tok: TokenKind::Else },
132 132
    { name: "export", tok: TokenKind::Export },
133 -
    { name: "extern", tok: TokenKind::Extern },
134 133
    { name: "false", tok: TokenKind::False },
135 134
    { name: "fn", tok: TokenKind::Fn },
136 135
    { name: "for", tok: TokenKind::For },
137 136
    { name: "i16", tok: TokenKind::I16 },
138 137
    { name: "i32", tok: TokenKind::I32 },
test/tests/ecall.i64.rad +1 -1
1 1
//! returns: 0
2 2
3 -
@intrinsic extern fn ecall(number: u32, arg1: i64, arg2: i64, arg3: i64, arg4: i64) -> i64;
3 +
@intrinsic fn ecall(number: u32, arg1: i64, arg2: i64, arg3: i64, arg4: i64) -> i64;
4 4
5 5
/// Test that ecall can pass and return i64 values.
6 6
@default fn main() -> i32 {
7 7
    // ecall(64, fd, buf, len, 0) = write(fd, buf, len).
8 8
    let msg: *[u8] = "ok\n";
test/tests/externfn.rad +1 -1
1 -
extern fn externalFunc(x: i32) -> i32;
1 +
fn externalFunc(x: i32) -> i32;
test/tests/intrinsic.ebreak.rad +1 -1
1 1
//! Test intrinsic ebreak lowering.
2 2
3 -
@intrinsic extern fn ebreak();
3 +
@intrinsic fn ebreak();
4 4
5 5
fn test() {
6 6
    ebreak();
7 7
}
test/tests/intrinsic.ecall.rad +1 -1
1 1
//! Test intrinsic ecall lowering.
2 2
3 -
@intrinsic extern fn ecall(num: u32, a0: i32, a1: i32, a2: i32, a3: i32) -> i32;
3 +
@intrinsic fn ecall(num: u32, a0: i32, a1: i32, a2: i32, a3: i32) -> i32;
4 4
5 5
fn test() -> i32 {
6 6
    return ecall(64, 1, 100, 5, 0);
7 7
}
vim/radiance.vim +1 -1
14 14
syntax match radianceComment "--.*$"
15 15
syntax keyword radianceTodo TODO FIXME contained containedin=radianceComment
16 16
17 17
" Keywords
18 18
syntax keyword radianceKeyword mod fn return if else while true false and or not case align static
19 -
syntax keyword radianceKeyword pub extern break continue use loop in for match nil undefined
19 +
syntax keyword radianceKeyword pub break continue use loop in for match nil undefined
20 20
syntax keyword radianceKeyword let mut as register device const log record union trait instance
21 21
syntax keyword radianceKeyword throws throw try catch panic assert super
22 22
syntax keyword radianceType i8 i16 i32 i64 u8 u16 u32 u64 f32 void bool bit opaque
23 23
24 24
" Double-quoted strings