Skip to main content

runmat_runtime/builtins/common/
identifiers.rs

1//! Shared MATLAB identifier and keyword compatibility helpers.
2
3/// Current MATLAB maximum identifier length reported by `namelengthmax`.
4pub const MATLAB_NAME_LENGTH_MAX: usize = 2048;
5
6/// MATLAB reserved keywords accepted by `iskeyword` and rejected by `isvarname`.
7pub const MATLAB_KEYWORDS: &[&str] = &[
8    "break",
9    "case",
10    "catch",
11    "classdef",
12    "continue",
13    "else",
14    "elseif",
15    "end",
16    "for",
17    "function",
18    "global",
19    "if",
20    "otherwise",
21    "parfor",
22    "persistent",
23    "return",
24    "spmd",
25    "switch",
26    "try",
27    "while",
28];
29
30pub fn is_matlab_keyword(name: &str) -> bool {
31    MATLAB_KEYWORDS.contains(&name)
32}
33
34pub fn is_valid_varname(name: &str) -> bool {
35    if name.chars().count() > MATLAB_NAME_LENGTH_MAX || is_matlab_keyword(name) {
36        return false;
37    }
38    let mut chars = name.chars();
39    let Some(first) = chars.next() else {
40        return false;
41    };
42    if !first.is_alphabetic() {
43        return false;
44    }
45    chars.all(|ch| ch == '_' || ch.is_alphanumeric())
46}
47
48#[cfg(test)]
49mod tests {
50    use super::*;
51
52    #[test]
53    fn keyword_list_matches_current_core_language_keywords() {
54        assert_eq!(MATLAB_KEYWORDS.len(), 20);
55        assert!(is_matlab_keyword("classdef"));
56        assert!(is_matlab_keyword("parfor"));
57        assert!(!is_matlab_keyword("plot"));
58    }
59
60    #[test]
61    fn valid_varname_uses_namelengthmax() {
62        assert!(is_valid_varname(&"a".repeat(MATLAB_NAME_LENGTH_MAX)));
63        assert!(!is_valid_varname(&"a".repeat(MATLAB_NAME_LENGTH_MAX + 1)));
64    }
65}