luaur_analysis/functions/
check_result_for_error.rs1use alloc::string::String;
2use core::ffi::c_int;
3use luaur_common::functions::format::format;
4use luaur_common::records::variant::Variant5;
5use luaur_vm::functions::lua_gettop::lua_gettop;
6use luaur_vm::functions::lua_isstring::lua_isstring;
7use luaur_vm::functions::lua_typename::lua_typename;
8use luaur_vm::macros::lua_tostring::lua_tostring;
9
10use crate::records::runtime_error::RuntimeError;
11use crate::records::type_function_error::TypeFunctionError;
12use crate::type_aliases::lua_state::lua_State;
13use luaur_ast::records::location::Location;
14
15pub fn check_result_for_error(
16 L: *mut lua_State,
17 type_function_name: &str,
18 lua_result: c_int,
19) -> Option<TypeFunctionError> {
20 match lua_result {
21 0 => None, 1 | 3 => Some(
23 TypeFunctionError::type_function_error_location_type_function_error_data(
24 Location::new(Default::default(), Default::default()),
25 Variant5::V2(RuntimeError::new(format(format_args!(
26 "'{}' type function errored: unexpected yield or break",
27 type_function_name
28 )))),
29 ),
30 ), _ => {
32 if unsafe { lua_gettop(L as *mut luaur_vm::records::lua_state::lua_State) } == 0 {
33 Some(
34 TypeFunctionError::type_function_error_location_type_function_error_data(
35 Location::new(Default::default(), Default::default()),
36 Variant5::V2(RuntimeError::new(format(format_args!(
37 "'{}' type function errored unexpectedly",
38 type_function_name
39 )))),
40 ),
41 )
42 } else if unsafe { lua_isstring(L as *mut luaur_vm::records::lua_state::lua_State, -1) }
43 != 0
44 {
45 let err_str =
46 unsafe { lua_tostring!(L as *mut luaur_vm::records::lua_state::lua_State, -1) };
47 let err_str = unsafe { core::ffi::CStr::from_ptr(err_str).to_string_lossy() };
48 Some(
49 TypeFunctionError::type_function_error_location_type_function_error_data(
50 Location::new(Default::default(), Default::default()),
51 Variant5::V2(RuntimeError::new(format(format_args!(
52 "'{}' type function errored at runtime: {}",
53 type_function_name, err_str
54 )))),
55 ),
56 )
57 } else {
58 let err_type =
59 unsafe { lua_typename(L as *mut luaur_vm::records::lua_state::lua_State, -1) };
60 let err_type = unsafe { core::ffi::CStr::from_ptr(err_type).to_string_lossy() };
61 Some(
62 TypeFunctionError::type_function_error_location_type_function_error_data(
63 Location::new(Default::default(), Default::default()),
64 Variant5::V2(RuntimeError::new(format(format_args!(
65 "'{}' type function errored at runtime: raised an error of type {}",
66 type_function_name, err_type
67 )))),
68 ),
69 )
70 }
71 }
72 }
73}