├── .clang-tidy ├── .editorconfig ├── .gitattributes ├── .github ├── FUNDING.yml └── workflows │ └── main.yml ├── .gitignore ├── .gitmodules ├── CMakeLists.txt ├── CMakeSettings.json ├── CODESTYLE.md ├── CODE_OF_CONDUCT.md ├── LICENSE ├── LICENSE_STDLIB ├── README.md ├── benchmarks └── stdlib │ └── sort │ └── quicksort.c3 ├── build-with-docker.sh ├── c3c.1 ├── dependencies └── miniz │ ├── miniz.c │ └── miniz.h ├── docker └── Dockerfile ├── flake.lock ├── flake.nix ├── git_hash.cmake ├── lib └── std │ ├── ascii.c3 │ ├── atomic.c3 │ ├── atomic_nolibc.c3 │ ├── bits.c3 │ ├── collections │ ├── anylist.c3 │ ├── bitset.c3 │ ├── elastic_array.c3 │ ├── enummap.c3 │ ├── enumset.c3 │ ├── hashmap.c3 │ ├── linkedlist.c3 │ ├── list.c3 │ ├── list_common.c3 │ ├── map.c3 │ ├── maybe.c3 │ ├── object.c3 │ ├── priorityqueue.c3 │ ├── range.c3 │ ├── ringbuffer.c3 │ └── tuple.c3 │ ├── compression │ └── qoi.c3 │ ├── core │ ├── allocators │ │ ├── arena_allocator.c3 │ │ ├── dynamic_arena.c3 │ │ ├── heap_allocator.c3 │ │ ├── libc_allocator.c3 │ │ ├── on_stack_allocator.c3 │ │ ├── temp_allocator.c3 │ │ └── tracking_allocator.c3 │ ├── array.c3 │ ├── bitorder.c3 │ ├── builtin.c3 │ ├── builtin_comparison.c3 │ ├── cinterop.c3 │ ├── conv.c3 │ ├── dstring.c3 │ ├── env.c3 │ ├── mem.c3 │ ├── mem_allocator.c3 │ ├── os │ │ └── wasm_memory.c3 │ ├── private │ │ ├── cpu_detect.c3 │ │ ├── macho_runtime.c3 │ │ └── main_stub.c3 │ ├── runtime.c3 │ ├── runtime_benchmark.c3 │ ├── runtime_test.c3 │ ├── sanitizer │ │ ├── asan.c3 │ │ ├── sanitizer.c3 │ │ └── tsan.c3 │ ├── string.c3 │ ├── string_iterator.c3 │ ├── string_to_real.c3 │ ├── test.c3 │ ├── types.c3 │ └── values.c3 │ ├── crypto │ ├── crypto.c3 │ ├── dh.c3 │ └── rc4.c3 │ ├── encoding │ ├── base32.c3 │ ├── base64.c3 │ ├── csv.c3 │ ├── encoding.c3 │ ├── hex.c3 │ └── json.c3 │ ├── hash │ ├── adler32.c3 │ ├── crc32.c3 │ ├── crc64.c3 │ ├── fnv32a.c3 │ ├── fnv64a.c3 │ ├── hmac.c3 │ ├── md5.c3 │ ├── sha1.c3 │ └── sha256.c3 │ ├── io │ ├── bits.c3 │ ├── file.c3 │ ├── formatter.c3 │ ├── formatter_private.c3 │ ├── io.c3 │ ├── os │ │ ├── chdir.c3 │ │ ├── file_libc.c3 │ │ ├── file_nolibc.c3 │ │ ├── fileinfo.c3 │ │ ├── getcwd.c3 │ │ ├── ls.c3 │ │ ├── mkdir.c3 │ │ ├── rmdir.c3 │ │ ├── rmtree.c3 │ │ └── temp_directory.c3 │ ├── path.c3 │ ├── stream.c3 │ └── stream │ │ ├── buffer.c3 │ │ ├── bytebuffer.c3 │ │ ├── bytereader.c3 │ │ ├── bytewriter.c3 │ │ ├── limitreader.c3 │ │ ├── multireader.c3 │ │ ├── multiwriter.c3 │ │ ├── scanner.c3 │ │ └── teereader.c3 │ ├── libc │ ├── libc.c3 │ ├── libc_extra.c3 │ ├── os │ │ ├── darwin.c3 │ │ ├── errno.c3 │ │ ├── freebsd.c3 │ │ ├── linux.c3 │ │ ├── posix.c3 │ │ └── win32.c3 │ └── termios.c3 │ ├── math │ ├── bigint.c3 │ ├── math.c3 │ ├── math_builtin.c3 │ ├── math_complex.c3 │ ├── math_easings.c3 │ ├── math_i128.c3 │ ├── math_libc.c3 │ ├── math_matrix.c3 │ ├── math_nolibc │ │ ├── __cos.c3 │ │ ├── __cosdf.c3 │ │ ├── __fmod.c3 │ │ ├── __sin.c3 │ │ ├── __sindf.c3 │ │ ├── __tan.c3 │ │ ├── __tandf.c3 │ │ ├── acos.c3 │ │ ├── asin.c3 │ │ ├── atan.c3 │ │ ├── atanh.c3 │ │ ├── ceil.c3 │ │ ├── cos.c3 │ │ ├── exp.c3 │ │ ├── exp2.c3 │ │ ├── fabs.c3 │ │ ├── floor.c3 │ │ ├── frexp.c3 │ │ ├── ldexp.c3 │ │ ├── log.c3 │ │ ├── log1p.c3 │ │ ├── math_nolibc.c3 │ │ ├── pow.c3 │ │ ├── rempi.c3 │ │ ├── round.c3 │ │ ├── scalbn.c3 │ │ ├── sin.c3 │ │ ├── sincos.c3 │ │ ├── tan.c3 │ │ ├── trig.c3 │ │ └── trunc.c3 │ ├── math_quaternion.c3 │ ├── math_random.c3 │ ├── math_vector.c3 │ ├── random │ │ ├── math.lcg.c3 │ │ ├── math.mcg.c3 │ │ ├── math.msws.c3 │ │ ├── math.pcg.c3 │ │ ├── math.seeder.c3 │ │ ├── math.sfc.c3 │ │ └── math.simple_random.c3 │ └── uuid.c3 │ ├── net │ ├── inetaddr.c3 │ ├── net.c3 │ ├── os │ │ ├── common.c3 │ │ ├── darwin.c3 │ │ ├── linux.c3 │ │ ├── posix.c3 │ │ └── win32.c3 │ ├── socket.c3 │ ├── socket_private.c3 │ ├── tcp.c3 │ ├── udp.c3 │ ├── url.c3 │ └── url_encoding.c3 │ ├── os │ ├── backtrace.c3 │ ├── cpu.c3 │ ├── env.c3 │ ├── linux │ │ ├── heap.c3 │ │ └── linux.c3 │ ├── macos │ │ ├── cf_allocator.c3 │ │ ├── cf_array.c3 │ │ ├── cocoa.c3 │ │ ├── core_foundation.c3 │ │ ├── darwin.c3 │ │ ├── heap.c3 │ │ └── objc.c3 │ ├── posix │ │ ├── files.c3 │ │ ├── general.c3 │ │ ├── heap.c3 │ │ ├── process.c3 │ │ └── threads.c3 │ ├── subprocess.c3 │ └── win32 │ │ ├── files.c3 │ │ ├── gdi.c3 │ │ ├── general.c3 │ │ ├── heap.c3 │ │ ├── process.c3 │ │ ├── types.c3 │ │ ├── windef.c3 │ │ ├── winuser.c3 │ │ └── wsa.c3 │ ├── sort │ ├── binarysearch.c3 │ ├── countingsort.c3 │ ├── insertionsort.c3 │ ├── quicksort.c3 │ ├── sort.c3 │ └── sorted.c3 │ ├── threads │ ├── buffered_channel.c3 │ ├── fixed_pool.c3 │ ├── os │ │ ├── cpu.c3 │ │ ├── thread_none.c3 │ │ ├── thread_posix.c3 │ │ └── thread_win32.c3 │ ├── pool.c3 │ ├── thread.c3 │ └── unbuffered_channel.c3 │ └── time │ ├── clock.c3 │ ├── datetime.c3 │ ├── format.c3 │ ├── os │ ├── time_darwin.c3 │ ├── time_posix.c3 │ └── time_win32.c3 │ └── time.c3 ├── msvc_build_libraries.py ├── nix ├── default.nix └── shell.nix ├── project_suggestions.md ├── releasenotes.md ├── resources ├── castrules.md ├── examples │ ├── args.c3 │ ├── base64.c3 │ ├── benchmarks.c3 │ ├── binarydigits.c3 │ ├── brainfk.c3 │ ├── constants.c3 │ ├── contextfree │ │ ├── boolerr.c3 │ │ ├── cleanup.c3 │ │ ├── dynscope.c3 │ │ ├── guess_number.c3 │ │ └── multi.c3 │ ├── dynlib-test │ │ ├── add.c3 │ │ ├── test.c │ │ └── test.c3 │ ├── embedded │ │ └── riscv-qemu │ │ │ ├── Makefile │ │ │ ├── README.md │ │ │ ├── baremetal.ld │ │ │ ├── hello.c3 │ │ │ ├── semihost.c3 │ │ │ ├── start.s │ │ │ └── uart.c3 │ ├── factorial_macro.c3 │ ├── fannkuch-redux.c3 │ ├── fannkuch-redux2.c3 │ ├── fasta.c3 │ ├── gameoflife.c3 │ ├── hash.c3 │ ├── hello_world.txt │ ├── hello_world_many.c3 │ ├── levenshtein.c3 │ ├── load_world.c3 │ ├── ls.c3 │ ├── mandelbrot.c3 │ ├── map.c3 │ ├── nbodies.c3 │ ├── nolibc-freebsd │ │ ├── hello_world.c3 │ │ └── project.json │ ├── nolibc │ │ ├── hello_world.c3 │ │ └── project.json │ ├── notworking │ │ ├── http.c3 │ │ ├── madlibs.c3 │ │ └── window.c3 │ ├── opengl │ │ ├── .gitignore │ │ ├── LICENSE │ │ ├── README.md │ │ ├── docs │ │ │ └── .gitkeep │ │ ├── lib │ │ │ └── .gitkeep │ │ ├── project.json │ │ ├── resources │ │ │ └── .gitkeep │ │ ├── scripts │ │ │ └── .gitkeep │ │ ├── src │ │ │ ├── gl │ │ │ │ └── gl.c3 │ │ │ ├── glfw │ │ │ │ └── glfw.c3 │ │ │ └── triangle.c3 │ │ └── test │ │ │ └── .gitkeep │ ├── plus_minus.c3 │ ├── process.c3 │ ├── project_all_settings.json │ ├── raylib │ │ ├── raylib_arkanoid.c3 │ │ ├── raylib_snake.c3 │ │ └── raylib_tetris.c3 │ ├── retry.c3 │ ├── spectralnorm.c3 │ ├── stacktrace_example.c3 │ ├── staticlib-test │ │ ├── add.c3 │ │ ├── test.c │ │ └── test.c3 │ ├── swap.c3 │ ├── time.c3 │ └── timeit.c3 ├── grammar │ ├── Makefile │ ├── c3.l │ ├── check_grammar.sh │ └── grammar.y ├── images │ └── vkQuake.png ├── linux_stack.c3 ├── msvc_stack.c3 ├── rosettacode │ ├── antiprime.c3 │ ├── helloworld.c3 │ └── quine.c3 ├── testfragments │ ├── allocators_testing.c3 │ ├── bigint.c3 │ ├── demo1.c3 │ ├── diagnostic.c3 │ ├── helloworld.c3 │ ├── pwd2.c3 │ ├── raylibtest.c3 │ ├── test.c3 │ ├── tmem.c3 │ ├── toposort.c3 │ └── wasm4.c3 └── testproject │ ├── csource │ └── test.c │ ├── lib │ ├── clib.c3l │ │ ├── clib.c3i │ │ ├── hello2.c │ │ ├── manifest.json │ │ └── whitespace test.c │ └── clib2.c3l │ ├── project.json │ ├── scripts │ ├── scriptme.c3 │ └── scripts.md │ └── src │ ├── bar.c3 │ ├── foo.c3 │ ├── hello_world.c3 │ └── zab.c3 ├── src ├── build │ ├── build.h │ ├── build_internal.h │ ├── build_options.c │ ├── builder.c │ ├── common_build.c │ ├── libraries.c │ ├── project.c │ ├── project.h │ ├── project_creation.c │ └── project_manipulation.c ├── compiler │ ├── abi │ │ ├── c_abi.c │ │ ├── c_abi_aarch64.c │ │ ├── c_abi_riscv.c │ │ ├── c_abi_wasm.c │ │ ├── c_abi_win64.c │ │ ├── c_abi_x64.c │ │ └── c_abi_x86.c │ ├── asm │ │ ├── aarch64.h │ │ ├── riscv.h │ │ └── x86.h │ ├── asm_target.c │ ├── ast.c │ ├── bigint.c │ ├── c_abi_internal.h │ ├── c_codegen.c │ ├── c_codegen_internal.h │ ├── codegen_asm.c │ ├── codegen_general.c │ ├── codegen_internal.h │ ├── compiler.c │ ├── compiler.h │ ├── compiler_internal.h │ ├── context.c │ ├── copying.c │ ├── decltable.c │ ├── diagnostics.c │ ├── dwarf.h │ ├── enums.h │ ├── expr.c │ ├── float.c │ ├── headers.c │ ├── json_output.c │ ├── lexer.c │ ├── linker.c │ ├── llvm_codegen.c │ ├── llvm_codegen_builtins.c │ ├── llvm_codegen_debug_info.c │ ├── llvm_codegen_expr.c │ ├── llvm_codegen_function.c │ ├── llvm_codegen_instr.c │ ├── llvm_codegen_internal.h │ ├── llvm_codegen_internal_impl.h │ ├── llvm_codegen_module.c │ ├── llvm_codegen_stmt.c │ ├── llvm_codegen_storeload.c │ ├── llvm_codegen_type.c │ ├── llvm_codegen_value.c │ ├── mac_support.c │ ├── module.c │ ├── number.c │ ├── parse_expr.c │ ├── parse_global.c │ ├── parse_stmt.c │ ├── parser.c │ ├── parser_internal.h │ ├── sema_asm.c │ ├── sema_builtins.c │ ├── sema_casts.c │ ├── sema_const.c │ ├── sema_decls.c │ ├── sema_errors.c │ ├── sema_expr.c │ ├── sema_initializers.c │ ├── sema_internal.h │ ├── sema_liveness.c │ ├── sema_name_resolution.c │ ├── sema_passes.c │ ├── sema_stmts.c │ ├── sema_types.c │ ├── semantic_analyser.c │ ├── source_file.c │ ├── subprocess.c │ ├── subprocess.h │ ├── symtab.c │ ├── target.c │ ├── target.h │ ├── tokens.c │ ├── types.c │ └── windows_support.c ├── compiler_tests │ ├── benchmark.c │ ├── benchmark.h │ ├── shorttest.c │ ├── tests.c │ └── tests.h ├── main.c ├── utils │ ├── common.h │ ├── cpus.c │ ├── errors.c │ ├── file_utils.c │ ├── find_msvc.c │ ├── hostinfo.c │ ├── hostinfo.h │ ├── http.c │ ├── json.c │ ├── json.h │ ├── lib.h │ ├── malloc.c │ ├── malloc.h │ ├── stringutils.c │ ├── taskqueue.c │ ├── time.c │ ├── unzipper.c │ ├── vmem.c │ ├── vmem.h │ ├── whereami.c │ └── whereami.h └── version.h ├── test ├── src │ └── tester.py ├── test_suite │ ├── abi │ │ ├── aarch64_args.c3t │ │ ├── aarch64_hfa_args.c3t │ │ ├── aarch_ret_small_struct.c3t │ │ ├── avx512fp16-abi.c3t │ │ ├── darwin64_avx.c3t │ │ ├── darwin64_avx512.c3t │ │ ├── darwin64_sret.c3t │ │ ├── darwin64_sse.c3t │ │ ├── darwin_arg.c3t │ │ ├── darwin_return_boolarray.c3t │ │ ├── darwinx64_1.c3t │ │ ├── darwinx64_2.c3t │ │ ├── linking_extern.c3t │ │ ├── literal_load.c3t │ │ ├── literal_load_aarch64.c3t │ │ ├── literal_load_mingw.c3t │ │ ├── macho_section.c3t │ │ ├── macho_section_attributes.c3 │ │ ├── pass_large_aarch.c3t │ │ ├── riscv32-ilp32-abi.c3t │ │ ├── riscv32-ilp32-ilp32f-abi-1.c3t │ │ ├── riscv32-ilp32-ilp32f-abi-2.c3t │ │ ├── riscv32-ilp32-ilp32f-ilp32d-abi-1.c3t │ │ ├── riscv32-ilp32-ilp32f-ilp32d-abi-2.c3t │ │ ├── riscv32-ilp32-ilp32f-ilp32d-abi-3.c3t │ │ ├── riscv32-ilp32d-abi.c3t │ │ ├── riscv32-ilp32f-abi.c3t │ │ ├── riscv32-ilp32f-ilp32d-abi-1.c3t │ │ ├── riscv32-ilp32f-ilp32d-abi-2.c3t │ │ ├── riscv64-lp64-abi.c3t │ │ ├── riscv64-lp64-lp64f-abi-1.c3t │ │ ├── riscv64-lp64-lp64f-abi-2.c3t │ │ ├── riscv64-lp64-lp64f-lp64d-abi-1.c3t │ │ ├── riscv64-lp64-lp64f-lp64d-abi-2.c3t │ │ ├── riscv64-lp64-lp64f-lp64d-abi-3.c3t │ │ ├── riscv64-lp64d-abi.c3t │ │ ├── riscv64-lp64f-lp64d-abi-1.c3t │ │ ├── riscv64-lp64f-lp64d-abi-2.c3t │ │ ├── small_struct_x64.c3t │ │ ├── sysv_abi_avx.c3t │ │ ├── sysv_abi_noavx.c3t │ │ ├── sysv_direct_coerce.c3t │ │ ├── test_sret.c3t │ │ ├── union_x64.c3t │ │ ├── vec2_aarch64.c3t │ │ ├── vec2_wasm.c3t │ │ ├── vec2_x64.c3t │ │ ├── wasm_extern.c3t │ │ └── x64alignarray.c3t │ ├── any │ │ ├── any_in_any.c3t │ │ ├── casting_voidptr_to_any.c3 │ │ ├── generic_interface.c3 │ │ ├── interface_no_fn.c3 │ │ ├── interface_no_method_body_1536.c3 │ │ ├── interface_ptr.c3 │ │ ├── variant_assign.c3t │ │ ├── variant_switch.c3t │ │ └── variant_test.c3t │ ├── arrays │ │ ├── array_bounds_check.c3t │ │ ├── array_casts.c3t │ │ ├── array_comparison.c3t │ │ ├── array_comparison_2.c3t │ │ ├── array_indexing.c3 │ │ ├── array_invalid_casts.c3 │ │ ├── array_literal.c3t │ │ ├── array_struct.c3t │ │ ├── complex_array_const.c3t │ │ ├── complex_inferred_array.c3t │ │ ├── global_array_non_const.c3 │ │ ├── global_init.c3t │ │ ├── global_init_array_out_of_range.c3 │ │ ├── index_from_back.c3t │ │ ├── index_into_global.c3t │ │ ├── inferred_array_err.c3 │ │ ├── inferred_array_err2.c3 │ │ ├── inferred_array_optional.c3t │ │ ├── inferred_subarray.c3 │ │ ├── negative_array.c3 │ │ └── slice.c3 │ ├── asm │ │ ├── asm_bit_rv.c3t │ │ ├── asm_imm_err_rv.c3 │ │ ├── asm_intr_rv.c3t │ │ ├── asm_jump_rv.c3t │ │ ├── asm_load_rv.c3t │ │ ├── asm_load_rv64.c3t │ │ ├── asm_math_rv.c3t │ │ ├── asm_ops_x64_1.c3t │ │ ├── asm_ops_x64_2.c3t │ │ ├── asm_regression.c3t │ │ ├── asm_set_rv.c3t │ │ ├── asm_shift_rv.c3t │ │ ├── asm_store_rv.c3t │ │ ├── naked.c3t │ │ ├── sideeffect.c3t │ │ └── syscall.c3t │ ├── assert │ │ ├── assert_variants.c3t │ │ ├── assert_with_void.c3 │ │ ├── assertf.c3t │ │ ├── global_static_assert_not_constant.c3 │ │ ├── local_static_assert_not_constant.c3 │ │ ├── static_assert.c3 │ │ ├── unreachable.c3t │ │ └── unreachable_in_macro.c3t │ ├── assignment │ │ ├── alignment_index.c3t │ │ ├── int_assign.c3t │ │ └── var_variable.c3 │ ├── attributes │ │ ├── attr_link_err.c3 │ │ ├── attr_not_imported.c3 │ │ ├── attribute_params.c3 │ │ ├── attribute_path.c3 │ │ ├── attribute_visibility.c3t │ │ ├── attributes_repeat_param.c3t │ │ ├── call_attribute_error_eos.c3 │ │ ├── recursive_attributes.c3 │ │ ├── user_defined_attributes.c3t │ │ ├── wasm_import.c3t │ │ └── wasm_module.c3 │ ├── bitstruct │ │ ├── address_of_bitstruct.c3 │ │ ├── anon_bitstruct_name_overlap.c3 │ │ ├── array_with_boolean.c3t │ │ ├── bistruct_cast_wrong_size.c3 │ │ ├── bitfield_access.c3t │ │ ├── bitstruct_access_signed.c3t │ │ ├── bitstruct_anon_in_struct_ok.c3t │ │ ├── bitstruct_arrays.c3t │ │ ├── bitstruct_arrays_be.c3t │ │ ├── bitstruct_be.c3t │ │ ├── bitstruct_bool.c3t │ │ ├── bitstruct_cast_and_back.c3 │ │ ├── bitstruct_cast_const_init.c3t │ │ ├── bitstruct_direct_in_struct.c3t │ │ ├── bitstruct_general.c3 │ │ ├── bitstruct_in_subarray.c3t │ │ ├── bitstruct_init.c3 │ │ ├── bitstruct_init_bool.c3t │ │ ├── bitstruct_initializer.c3t │ │ ├── bitstruct_intcontainer.c3t │ │ ├── bitstruct_ops.c3t │ │ ├── bitstruct_overlap.c3 │ │ ├── bitstruct_simple.c3 │ │ ├── bitstruct_simple_err_decl.c3 │ │ ├── bitstruct_single_error.c3 │ │ ├── bitstruct_to_int.c3t │ │ ├── designated_initializer_with_bitstruct.c3t │ │ ├── embedded_bitstruct.c3t │ │ ├── invalid_bitstruct_member_types.c3 │ │ ├── invalid_bitstruct_name_other_ident.c3 │ │ ├── invalid_bitstruct_type.c3 │ │ ├── invalid_empty_struct_union.c3 │ │ ├── missing_bitstruct_type.c3 │ │ └── param_bitstruct.c3t │ ├── builtins │ │ ├── builtin_vector_abs.c3t │ │ ├── builtin_vector_min_max.c3t │ │ ├── builtin_with_optional.c3 │ │ ├── exacts.c3t │ │ ├── mem.c3t │ │ ├── overflows.c3t │ │ ├── prefetch.c3t │ │ ├── reduce_arithmetics.c3t │ │ ├── reverse_builtin.c3t │ │ ├── rounding_builtins.c3t │ │ ├── sat_builtins.c3t │ │ ├── shufflevector.c3t │ │ ├── simple_builtins.c3t │ │ ├── trap.c3t │ │ └── unaligned_load_store.c3t │ ├── cast │ │ ├── cast_bitstruct_etc.c3t │ │ ├── cast_from_ptr.c3t │ │ ├── cast_narrow_alias.c3t │ │ ├── cast_ok.c3 │ │ ├── cast_parse_fails.c3 │ │ ├── cast_parse_fails2.c3 │ │ ├── cast_ptr_vec_to_bool.c3t │ │ ├── cast_rcast.c3 │ │ ├── cast_slice_implicit.c3 │ │ ├── cast_string_to_infered_array.c3 │ │ ├── cast_struct.c3 │ │ ├── cast_struct_fails.c3 │ │ ├── cast_subarray.c3t │ │ ├── cast_to_failable.c3 │ │ ├── cast_untyped_list_error.c3 │ │ ├── implicit_array_ptr_conv.c3 │ │ ├── implicit_infer_len_cast.c3t │ │ ├── implicit_void_ptr_deep.c3 │ │ ├── inner_type_cast.c3 │ │ ├── top_down_cast_fails.c3 │ │ └── top_down_casts.c3t │ ├── clang │ │ ├── 2002-01_02.c3t │ │ ├── 2002-03.c3t │ │ ├── 2002-04.c3t │ │ └── 2002-07.c3t │ ├── comments │ │ └── simple_comments.c3 │ ├── compile_time │ │ ├── add_to_ct_undefined.c3 │ │ ├── compile_time_access_subscript.c3t │ │ ├── compile_time_array.c3t │ │ ├── compile_time_array_bug.c3t │ │ ├── compile_time_array_ref.c3t │ │ ├── compile_time_bitops.c3t │ │ ├── compile_time_pointers.c3t │ │ ├── compile_time_ptr_ref.c3t │ │ ├── compile_time_utf32.c3 │ │ ├── comptime_array_folding.c3t │ │ ├── concat_append.c3t │ │ ├── concat_append_extended_and_edit.c3t │ │ ├── concat_const.c3 │ │ ├── concat_slice_array.c3 │ │ ├── concat_slice_bytes.c3t │ │ ├── concat_test.c3t │ │ ├── concat_test_cases.c3 │ │ ├── concat_zero_slice.c3t │ │ ├── ct_and_or.c3 │ │ ├── ct_assert_bug.c3 │ │ ├── ct_builtin_time_date.c3t │ │ ├── ct_cast_example.c3t │ │ ├── ct_declaration_in_if.c3t │ │ ├── ct_else_else.c3 │ │ ├── ct_enum_values.c3t │ │ ├── ct_eval.c3t │ │ ├── ct_eval_sym.c3 │ │ ├── ct_eval_wrong.c3 │ │ ├── ct_for.c3t │ │ ├── ct_forach_with_defer.c3t │ │ ├── ct_foreach.c3t │ │ ├── ct_func.c3t │ │ ├── ct_funcptr.c3t │ │ ├── ct_if.c3t │ │ ├── ct_if_folding.c3t │ │ ├── ct_left_hand_assign.c3t │ │ ├── ct_memberof.c3t │ │ ├── ct_ordered_error.c3t │ │ ├── ct_string_functions.c3t │ │ ├── ct_subscript_inc.c3t │ │ ├── ct_subscript_op.c3t │ │ ├── ct_switch.c3t │ │ ├── ct_switch_errors.c3 │ │ ├── ct_switch_more_checks.c3 │ │ ├── ct_switch_top_level.c3t │ │ ├── ct_switch_type_check.c3t │ │ ├── ct_switch_type_errors.c3 │ │ ├── ct_through_constant.c3t │ │ ├── ct_vaexpr_assign.c3t │ │ ├── ct_value_from_access.c3t │ │ ├── cttype_reassign.c3t │ │ ├── deep_stringify.c3t │ │ ├── macro_compile_time_pseudo_evaluation.c3t │ │ ├── mod_ct.c3t │ │ ├── mod_in_other_scope.c3 │ │ ├── more_untyped_conversions.c3t │ │ ├── not_cost.c3 │ │ ├── not_yet_initialized.c3 │ │ ├── stringify.c3t │ │ ├── stringify2.c3t │ │ ├── ternary_folding.c3t │ │ ├── typed_ct_vars.c3t │ │ ├── typefrom.c3t │ │ ├── typefrom_errors.c3t │ │ ├── typeof_example.c3t │ │ ├── typeof_from_literal.c3 │ │ ├── untyped_conversions.c3t │ │ └── untyped_with_inferred.c3 │ ├── compile_time_introspection │ │ ├── alignof.c3t │ │ ├── defined.c3t │ │ ├── defined2.c3 │ │ ├── defined_2.c3t │ │ ├── defined_builtin.c3t │ │ ├── defined_err.c3 │ │ ├── defined_index.c3t │ │ ├── defined_subscript.c3 │ │ ├── nameof.c3t │ │ ├── nameof_err.c3 │ │ ├── offsetof.c3t │ │ ├── paramsof.c3t │ │ ├── parentof.c3t │ │ ├── qnameof.c3t │ │ ├── recursive_tag.c3 │ │ ├── sizeof.c3t │ │ ├── sizeof_errors.c3 │ │ ├── tag.c3t │ │ └── tag_1343.c3t │ ├── concurrency │ │ ├── atomic_load_store.c3t │ │ └── atomic_load_store_debug.c3t │ ├── constants │ │ ├── assign_to_const.c3 │ │ ├── byte_literal_fail_base64.c3 │ │ ├── byte_literal_fail_base64_2.c3 │ │ ├── byte_literal_fail_base64_4.c3 │ │ ├── byte_literal_fail_hex.c3 │ │ ├── byte_literals.c3t │ │ ├── char_literals.c3t │ │ ├── const_var_copy.c3t │ │ ├── constant_struct.c3 │ │ ├── constants.c3t │ │ ├── empty_byte_literal.c3 │ │ ├── float_type.c3t │ │ └── init_order.c3t │ ├── contracts │ │ ├── constant_out.c3 │ │ ├── ct_eval_of_ensure.c3 │ │ ├── ensure_unsigned.c3 │ │ ├── in_array.c3 │ │ ├── in_out.c3 │ │ ├── macro_ensure_static.c3 │ │ ├── out_subscript.c3 │ │ ├── pure.c3 │ │ ├── pure_calls.c3 │ │ ├── require_contract_loc.c3 │ │ └── simple_test.c3t │ ├── debug_symbols │ │ ├── constants.c3t │ │ ├── constants_mingw.c3t │ │ ├── ct_foreach.c3t │ │ ├── defer_macro.c3t │ │ └── foreach.c3t │ ├── defer │ │ ├── defer_and_expr_block.c3t │ │ ├── defer_catch_direct_error.c3t │ │ ├── defer_catch_err.c3t │ │ ├── defer_catch_mix.c3t │ │ ├── defer_catch_try.c3t │ │ ├── defer_nextcase.c3t │ │ ├── defer_single_stmt.c3 │ │ ├── defer_static_var.c3t │ │ ├── defer_try_catch.c3t │ │ ├── defer_with_catch.c3t │ │ ├── defer_with_rethrow.c3 │ │ └── defer_with_return.c3 │ ├── define │ │ ├── alias_typename.c3 │ │ ├── aliased_consts.c3t │ │ ├── common.c3 │ │ ├── common2.c3 │ │ ├── define_name_errors.c3 │ │ ├── forbidden_defines.c3 │ │ ├── test_at.c3 │ │ ├── test_at_alias.c3 │ │ ├── weak_alias_fails.c3 │ │ └── weak_aliases.c3 │ ├── distinct │ │ ├── disntinct_add_fail.c3 │ │ ├── distinct_add.c3 │ │ ├── distinct_function.c3t │ │ ├── distinct_function_call.c3 │ │ ├── distinct_inline_access.c3 │ │ ├── distinct_invalid.c3 │ │ ├── distinct_max.c3t │ │ ├── distinct_shift.c3t │ │ ├── distinct_slicing.c3 │ │ ├── distinct_struct.c3 │ │ ├── distinct_struct_array.c3 │ │ ├── distinct_sub.c3t │ │ ├── distinct_union.c3 │ │ ├── test_errors.c3 │ │ ├── test_ops_on_int.c3 │ │ └── test_ops_on_struct.c3 │ ├── dynamic │ │ ├── any_cast.c3 │ │ ├── duplicate_definition.c3 │ │ ├── dynamic_inherit_deep.c3t │ │ ├── dynamic_mismatch.c3 │ │ ├── dynamic_tracing.c3t │ │ ├── inherit_linux.c3t │ │ ├── inherit_macos.c3t │ │ ├── inline_protocol.c3 │ │ ├── null_and_protocol.c3t │ │ ├── overlapping_function_linux.c3t │ │ ├── overlapping_function_macos.c3t │ │ └── same_method_twice.c3 │ ├── embed │ │ └── embed_basic.c3t │ ├── enumerations │ │ ├── compile_time.c3t │ │ ├── enum_add_sub.c3t │ │ ├── enum_associated_value.c3t │ │ ├── enum_associated_values_other.c3t │ │ ├── enum_cast.c3t │ │ ├── enum_cast_error.c3 │ │ ├── enum_conversions.c3t │ │ ├── enum_invalid_param.c3 │ │ ├── enum_reflect_associated.c3t │ │ ├── enum_same_param.c3 │ │ ├── enum_signed_cast_swap.c3t │ │ ├── enum_values.c3t │ │ ├── enum_with_associated_value_decl.c3 │ │ ├── enum_with_const.c3t │ │ ├── inc_assign.c3t │ │ ├── inc_assign_fail.c3 │ │ ├── inline_enum_size.c3 │ │ ├── inline_enums.c3t │ │ ├── introspection_data_error.c3t │ │ ├── missing_type.c3 │ │ └── simple_inference.c3t │ ├── errors │ │ ├── anyfault_void.c3t │ │ ├── bitshift_failable.c3 │ │ ├── else_checks.c3t │ │ ├── else_struct.c3t │ │ ├── else_unreachable.c3t │ │ ├── else_unreachable_in_block.c3 │ │ ├── empty_fault.c3 │ │ ├── error_decl_ok.c3 │ │ ├── error_else.c3t │ │ ├── error_introspect.c3t │ │ ├── error_regression_2.c3t │ │ ├── error_semantic_fails.c3 │ │ ├── error_throw.c3 │ │ ├── error_union.c3 │ │ ├── failable_catch.c3t │ │ ├── fault_conv.c3t │ │ ├── general_error_regression.c3t │ │ ├── illegal_use_of_optional.c3 │ │ ├── invalid_cast_ct.c3 │ │ ├── lone_try.c3 │ │ ├── macro_err.c3t │ │ ├── macro_err2.c3t │ │ ├── macro_err3.c3t │ │ ├── macro_recurse_twice.c3 │ │ ├── missing_bang.c3 │ │ ├── mixed_decl.c3 │ │ ├── more_optional_discard.c3 │ │ ├── more_optional_tests.c3 │ │ ├── multiple_catch.c3t │ │ ├── no_common.c3 │ │ ├── optional_chained_init.c3t │ │ ├── optional_contracts.c3 │ │ ├── optional_designated.c3 │ │ ├── optional_discarded_func.c3 │ │ ├── optional_discarded_macro.c3 │ │ ├── optional_inits.c3t │ │ ├── optional_sizeof.c3 │ │ ├── optional_taddr_and_access.c3t │ │ ├── optional_untyped_list.c3 │ │ ├── optional_with_optional.c3t │ │ ├── or_and_rethrow.c3t │ │ ├── or_err_bool.c3t │ │ ├── precedence_err.c3 │ │ ├── printing_errors.c3t │ │ ├── rethrow.c3t │ │ ├── rethrow_macro.c3 │ │ ├── rethrow_mingw.c3t │ │ ├── rethrow_no_err.c3 │ │ ├── simple_static_failable.c3t │ │ ├── switch_default_catch.c3 │ │ ├── ternary_void_fault.c3t │ │ ├── try_assign.c3t │ │ ├── try_catch_if.c3t │ │ ├── try_catch_unwrapping_while_if.c3 │ │ ├── try_expr.c3t │ │ ├── try_unwrap_using_assert.c3 │ │ ├── try_with_assign_to_failable.c3 │ │ ├── try_with_chained_unwrap.c3t │ │ ├── try_with_chained_unwrap_errors.c3 │ │ ├── try_with_unwrap.c3t │ │ ├── try_with_unwrapper.c3t │ │ ├── try_with_weird_stuff.c3 │ │ └── type_optional_declaration_order.c3 │ ├── examples │ │ └── gameoflife.c3 │ ├── expression_block │ │ ├── expr_block_labelled_break.c3 │ │ ├── expr_block_no_assign.c3 │ │ ├── expression_block_break.c3 │ │ └── expression_block_no_end_return.c3 │ ├── expressions │ │ ├── 2002-02-13-ConditionalInCall.c3t │ │ ├── addr_compiles.c3t │ │ ├── addr_of_fails.c3 │ │ ├── arithmetics.c3 │ │ ├── arithmetics_sema_fail.c3 │ │ ├── assign.c3 │ │ ├── assign_deref_opt.c3 │ │ ├── assign_optional.c3t │ │ ├── assign_to_address.c3 │ │ ├── assignability.c3 │ │ ├── assignment_precedence.c3t │ │ ├── bit_op_on_bool.c3t │ │ ├── bool_conversions.c3t │ │ ├── call_arg_types.c3 │ │ ├── call_inline.c3t │ │ ├── casts │ │ │ ├── cast_const.c3 │ │ │ ├── cast_enum_const_to_distinct.c3 │ │ │ ├── cast_enum_to_various.c3 │ │ │ ├── cast_expr.c3t │ │ │ ├── cast_failable.c3 │ │ │ ├── cast_func_to_various.c3 │ │ │ ├── cast_implicit_inline_distinct.c3 │ │ │ ├── cast_to_nonscalar.c3 │ │ │ ├── cast_unknown.c3 │ │ │ ├── cast_vector_fail.c3 │ │ │ ├── enum_plus_minus.c3t │ │ │ ├── explicit_cast.c3 │ │ │ ├── failed_distinct_float_conversions.c3 │ │ │ ├── narrowing.c3 │ │ │ ├── narrowing_through_casts.c3 │ │ │ ├── struct_cast_and_distinct.c3 │ │ │ └── void_casting.c3 │ │ ├── chained_conditional.c3t │ │ ├── chained_ternary.c3t │ │ ├── check_implict_conversion_signed_unsigned.c3t │ │ ├── deref_access_null.c3t │ │ ├── elvis.c3t │ │ ├── enum_ct_sub.c3t │ │ ├── fail_index_usize.c3 │ │ ├── fmuladd.c3t │ │ ├── fmuladd_err.c3t │ │ ├── folding_ptr.c3t │ │ ├── incdec.c3t │ │ ├── incdec_overload.c3t │ │ ├── negate_int.c3 │ │ ├── negated_macro.c3t │ │ ├── no_valid_conversion_minus.c3 │ │ ├── not_in_wrong_position.c3 │ │ ├── optional_and_error.c3 │ │ ├── optional_ternary.c3t │ │ ├── parsed_numbers.c3t │ │ ├── plus_int.c3 │ │ ├── pointer_access.c3t │ │ ├── pointer_arith.c3 │ │ ├── pointer_conv_error.c3 │ │ ├── pointer_to_bool.c3 │ │ ├── rvalues.c3 │ │ ├── simple_float_sub_neg.c3t │ │ ├── strings.c3t │ │ ├── take_address.c3t │ │ ├── ternary_bool.c3t │ │ ├── ternary_infer.c3t │ │ ├── ternary_no_ident.c3 │ │ ├── ternary_void.c3t │ │ ├── test_ct_param_bug.c3 │ │ ├── type_support.c3t │ │ ├── underscore_errors.c3 │ │ ├── unsafe_comparisons.c3 │ │ └── void_arg.c3 │ ├── floats │ │ ├── convert_float.c3t │ │ ├── explicit_float_truncation_needed.c3 │ │ ├── float_exceeding_size.c3 │ │ ├── inf_nan.c3t │ │ └── mod.c3t │ ├── from_docs │ │ ├── examples_defer.c3t │ │ ├── examples_forswitch.c3t │ │ ├── examples_functionpointer.c3t │ │ ├── examples_if_catch.c3t │ │ ├── examples_macro_function.c3t │ │ └── examples_struct.c3 │ ├── functions │ │ ├── accidental_method_1448.c3 │ │ ├── after_vararg.c3 │ │ ├── assorted_tests.c3t │ │ ├── body_argument_fail.c3 │ │ ├── c_vararg_expansion.c3t │ │ ├── ct_named_params.c3t │ │ ├── default_param_fail.c3 │ │ ├── defered_default_arguments.c3t │ │ ├── distinct_fn_ptr_and_lambda.c3t │ │ ├── double_return.c3 │ │ ├── failable_param.c3 │ │ ├── func_ptr_conversion_alias.c3t │ │ ├── func_ptr_conversions_and_names.c3t │ │ ├── func_ptr_null.check.c3t │ │ ├── function_alias_llvm_check.c3t │ │ ├── function_reserved_name.c3 │ │ ├── invalid_param.c3 │ │ ├── macro_arguments.c3 │ │ ├── macro_expr_type.c3 │ │ ├── missing_first_paren.c3 │ │ ├── missing_fn.c3 │ │ ├── missing_return.c3 │ │ ├── missing_return_lambda.c3 │ │ ├── multisplat.c3t │ │ ├── naked_function.c3t │ │ ├── named_arg_order.c3 │ │ ├── param_doc_error.c3 │ │ ├── param_with_comma_at_end.c3 │ │ ├── pointer_escape.c3 │ │ ├── raw_splat.c3t │ │ ├── recursive_fn.c3 │ │ ├── recursive_through_generic.c3 │ │ ├── returning_void.c3t │ │ ├── simple_test.c3t │ │ ├── splat.c3t │ │ ├── splat_aarch64.c3t │ │ ├── splat_empty.c3t │ │ ├── splat_init.c3t │ │ ├── splat_mingw.c3t │ │ ├── splat_post_order.c3t │ │ ├── splat_raw.c3 │ │ ├── splat_untyped.c3t │ │ ├── static_vars.c3t │ │ ├── test_regression.c3t │ │ ├── test_regression_mingw.c3t │ │ ├── too_many_params.c3 │ │ ├── type_argument_live_1461.c3t │ │ ├── typeless_varargs.c3t │ │ ├── unsplat_named.c3 │ │ ├── vaarg_raw.c3 │ │ ├── vararg_and_named_tests.c3 │ │ ├── vararg_argument_fails.c3 │ │ ├── varargs.c3t │ │ ├── varargs_followed_by_named.c3t │ │ └── void_params.c3 │ ├── generic │ │ ├── different_generic_def.c3 │ │ ├── enum_in_other_module.c3t │ │ ├── enum_set_test.c3t │ │ ├── generic_builtin.c3t │ │ ├── generic_copy.c3t │ │ ├── generic_cyclic.c3 │ │ ├── generic_idents.c3t │ │ ├── generic_interface.c3t │ │ ├── generic_lambda_complex.c3t │ │ ├── generic_local.c3 │ │ ├── generic_num.c3t │ │ ├── generic_over_fn.c3t │ │ ├── generic_parsing.c3 │ │ ├── generic_recursion.c3t │ │ ├── generic_resolution_1402.c3t │ │ ├── generic_void.c3t │ │ ├── generic_with_comment.c3t │ │ ├── generic_with_enum.c3t │ │ ├── generic_without_param.c3 │ │ ├── implicit_import_of_generic.c3 │ │ ├── incorrect_argument_type.c3 │ │ ├── nested_typedef.c3t │ │ ├── used_without_param.c3 │ │ ├── used_without_param2.c3 │ │ └── used_without_param3.c3 │ ├── globals │ │ ├── ext_global_init.c3 │ │ ├── extern_const.c3t │ │ ├── external_global.c3t │ │ ├── global_align.c3t │ │ ├── global_extname.c3t │ │ ├── global_init.c3 │ │ ├── global_no_init.c3t │ │ ├── init_with_err.c3t │ │ ├── misplaced_const.c3 │ │ ├── recursive_globals.c3 │ │ ├── recursive_locals.c3 │ │ ├── self_referencing_local.c3 │ │ └── static_global.c3 │ ├── import │ │ ├── access_other_module.c3t │ │ ├── autoimport.c3 │ │ ├── import_error.c3 │ │ ├── import_error_multi.c3 │ │ ├── import_error_string.c3 │ │ ├── import_implicit.c3 │ │ ├── import_nonrecurse.c3 │ │ ├── import_same.c3 │ │ ├── import_twice.c3 │ │ └── import_works.c3t │ ├── initialize │ │ ├── init_non_resolved_type.c3 │ │ ├── initialize_bad_prio.c3 │ │ ├── initialize_finalize.c3t │ │ ├── initialize_jump.c3 │ │ ├── initialize_parse_error.c3 │ │ ├── initialize_prio.c3 │ │ └── initializer_var.c3t │ ├── initializer_lists │ │ ├── disallowed_lists.c3 │ │ ├── fasta.c3t │ │ ├── general_tests.c3t │ │ ├── indexing_into_complist.c3 │ │ ├── infer_with_init.c3t │ │ ├── init_any_interface.c3 │ │ ├── initializers_to_macros.c3 │ │ ├── ranges_to_dynamic.c3t │ │ ├── statics.c3t │ │ ├── subarrays.c3t │ │ ├── zero_inferred_array.c3 │ │ └── zero_init.c3t │ ├── lambda │ │ ├── ct_lambda.c3t │ │ ├── ct_lambda2.c3t │ │ ├── lambda_checks.c3 │ │ ├── lambda_in_macro.c3t │ │ ├── lambda_ref.c3t │ │ ├── nested_lambda_def.c3t │ │ ├── simple_lambda.c3t │ │ └── var_lambda.c3 │ ├── lexing │ │ ├── expected_directive.c3 │ │ ├── invalid_hex_in_hexarray.c3 │ │ ├── invalid_hex_in_hexarray2.c3 │ │ └── no_builtin.c3 │ ├── literals │ │ ├── bad_bitwidth.c3 │ │ ├── bin_literal.c3t │ │ ├── bin_literal2.c3t │ │ ├── literal_general.c3t │ │ ├── multi_unicode.c3 │ │ ├── radix_numbers_errors.c3 │ │ └── too_small.c3 │ ├── macro_methods │ │ ├── access.c3 │ │ ├── macro_method_different_args.c3t │ │ ├── macro_method_fails.c3 │ │ ├── macro_method_first_param.c3 │ │ └── macro_methods_defined_twice.c3 │ ├── macros │ │ ├── hash_ident.c3 │ │ ├── hash_ident_nested.c3t │ │ ├── hash_initializer.c3t │ │ ├── implicit_return_opt.c3 │ │ ├── macro_always_const.c3 │ │ ├── macro_body_as_value.c3 │ │ ├── macro_body_defer.c3t │ │ ├── macro_body_errors.c3 │ │ ├── macro_body_missing_type.c3 │ │ ├── macro_body_ref_hash_constant_type.c3t │ │ ├── macro_calls_prefix.c3 │ │ ├── macro_chained_return_void_optional.c3t │ │ ├── macro_common.c3t │ │ ├── macro_convert_literal.c3 │ │ ├── macro_defer_exit.c3t │ │ ├── macro_defer_scope.c3t │ │ ├── macro_defer_with_body.c3t │ │ ├── macro_failable_return_rethrow.c3t │ │ ├── macro_import_res_private.c3t │ │ ├── macro_import_resolution.c3 │ │ ├── macro_nested_labels.c3t │ │ ├── macro_ref_body_err1.c3 │ │ ├── macro_ref_body_err2.c3 │ │ ├── macro_resolution.c3 │ │ ├── macro_rtype.c3 │ │ ├── macro_tagof.c3t │ │ ├── macro_typed_varargs.c3t │ │ ├── macro_untyped_varargs.c3 │ │ ├── macro_untyped_varargs_2.c3t │ │ ├── macro_vasplat.c3t │ │ ├── macro_with_body.c3t │ │ ├── macro_with_body_err.c3 │ │ ├── modify_ct_param.c3 │ │ ├── no_body.c3 │ │ ├── ref_macro_method.c3 │ │ ├── ref_vector.c3t │ │ ├── trailing_body_const.c3t │ │ ├── type_params.c3t │ │ ├── typed_hash_access.c3 │ │ ├── unifying_implicit_void.c3t │ │ ├── userland_bitcast.c3t │ │ └── vasplat_function_call.c3 │ ├── methods │ │ ├── access.c3 │ │ ├── access_private_method.c3 │ │ ├── dynamic_method_fails.c3 │ │ ├── enum_distinct_err_methods.c3t │ │ ├── extending_with_visibility.c3 │ │ ├── extending_with_visibility_fail.c3 │ │ ├── extending_with_visibility_fail_private.c3 │ │ ├── extension_method.c3t │ │ ├── extension_method_already_exist.c3 │ │ ├── extension_method_check.c3 │ │ ├── extension_method_generic.c3 │ │ ├── extension_method_in_other_modules.c3t │ │ ├── method_extension_in_conditional_module.c3 │ │ ├── method_from_var.c3 │ │ ├── method_name_collision.c3 │ │ ├── method_ref_for_extension_method.c3 │ │ ├── methods_defined_twice.c3 │ │ ├── methods_with_inferred_type.c3t │ │ ├── operator_assign_mutate.c3t │ │ ├── operator_defined_twice.c3 │ │ ├── operator_inc.c3t │ │ ├── operator_mismatch.c3 │ │ ├── self_methods_null.c3t │ │ └── unsupported_operator.c3 │ ├── module │ │ ├── missing_semi.c3 │ │ ├── module_bad_path_ident.c3 │ │ ├── module_bad_path_invalid.c3 │ │ ├── module_bad_path_keyword.c3 │ │ ├── module_error_string.c3 │ │ ├── module_generic_mixing.c3 │ │ ├── module_section_export.c3t │ │ ├── module_start_bad_ident.c3 │ │ ├── module_start_invalid.c3 │ │ ├── module_start_keyword.c3 │ │ ├── private_module.c3 │ │ └── unknown_modules.c3 │ ├── overloading │ │ ├── construct_op_zero_args.c3 │ │ ├── construct_operator.c3t │ │ ├── set_not_set_overload.c3t │ │ └── set_overload.c3t │ ├── pointers │ │ ├── array_pointer_decay.c3t │ │ ├── const_pointer.c3t │ │ ├── const_ref.c3t │ │ ├── pointer_index.c3t │ │ └── subarray_variant_to_ptr.c3t │ ├── precedence │ │ └── required_parens.c3 │ ├── regression │ │ └── crash_on_right_paren_macro.c3 │ ├── safe │ │ ├── deref.c3t │ │ └── detect_invalid_deref_return.c3 │ ├── slices │ │ ├── array_to_const_err.c3 │ │ ├── array_to_const_slice.c3t │ │ ├── slice_assign.c3t │ │ ├── slice_assign2.c3t │ │ ├── slice_checks.c3t │ │ ├── slice_comparison.c3t │ │ ├── slice_conv_byte.c3t │ │ ├── slice_init.c3t │ │ ├── slice_inline.c3t │ │ ├── slice_len_error.c3 │ │ ├── slice_negative_len.c3 │ │ ├── slice_offset.c3t │ │ ├── slice_offset_neg_end.c3t │ │ ├── slice_offset_neg_start.c3t │ │ ├── slice_optional.c3t │ │ ├── slice_optional_index.c3t │ │ ├── slice_start.c3t │ │ ├── slice_syntax.c3 │ │ ├── slice_to_slice_assign.c3t │ │ ├── slice_to_slice_conv_err.c3t │ │ ├── slice_to_slice_vector_assign.c3t │ │ ├── sub_array_init.c3 │ │ ├── subscript_check_1519.c3t │ │ └── various_const_slicing.c3t │ ├── statements │ │ ├── binary_fail.c3 │ │ ├── call_missing_paren.c3 │ │ ├── comparison_widening.c3t │ │ ├── conditional_return.c3 │ │ ├── const_statements.c3t │ │ ├── custom_foreach_with_ref.c3t │ │ ├── dead_statements.c3t │ │ ├── default_args.c3 │ │ ├── default_macro_argc.c3t │ │ ├── defer_break.c3t │ │ ├── defer_break_simple.c3t │ │ ├── defer_break_switch.c3t │ │ ├── defer_continue_bug.c3t │ │ ├── defer_do_while.c3t │ │ ├── defer_hash.c3t │ │ ├── defer_if_try_copy.c3t │ │ ├── defer_in_block.c3t │ │ ├── defer_in_defer.c3t │ │ ├── defer_in_defer2.c3t │ │ ├── defer_next_switch.c3t │ │ ├── defer_return.c3t │ │ ├── defer_test.c3 │ │ ├── defer_with_loop.c3t │ │ ├── do_without_compound.c3 │ │ ├── exhaustive_switch.c3t │ │ ├── fallthough_do.c3t │ │ ├── for.c3 │ │ ├── for_empty.c3 │ │ ├── for_errors.c3 │ │ ├── for_statement_placement.c3 │ │ ├── for_with_extra_declarations.c3 │ │ ├── foreach_break.c3t │ │ ├── foreach_common.c3t │ │ ├── foreach_custom.c3t │ │ ├── foreach_custom_errors.c3 │ │ ├── foreach_custom_macro.c3t │ │ ├── foreach_distinct_iterable.c3t │ │ ├── foreach_distinct_pointer_1506.c3 │ │ ├── foreach_errors.c3 │ │ ├── foreach_more_implementations.c3t │ │ ├── foreach_parse_error.c3 │ │ ├── foreach_r_break.c3t │ │ ├── foreach_r_common.c3t │ │ ├── foreach_r_custom.c3t │ │ ├── foreach_r_custom_errors.c3 │ │ ├── foreach_r_custom_macro.c3t │ │ ├── foreach_r_errors.c3 │ │ ├── foreach_r_parse_error.c3 │ │ ├── foreach_r_with_error.c3 │ │ ├── foreach_with_error.c3 │ │ ├── foreach_wrong_index.c3 │ │ ├── if_decl.c3 │ │ ├── if_only_throw.c3t │ │ ├── if_single.c3 │ │ ├── if_tests.c3t │ │ ├── if_while_do_error.c3 │ │ ├── infinite_do_while.c3t │ │ ├── label_errors.c3 │ │ ├── labelled_continue_for.c3t │ │ ├── nextcase_const.c3t │ │ ├── nextcase_default.c3t │ │ ├── nextcase_missing_case.c3 │ │ ├── nextcase_no_switch.c3 │ │ ├── ranged_switch.c3t │ │ ├── return_stmt.c3 │ │ ├── return_switch.c3t │ │ ├── return_with_other_at_end.c3 │ │ ├── simple_do.c3t │ │ ├── switch_error_fallthrough.c3 │ │ ├── switch_error_range.c3 │ │ ├── switch_errors.c3 │ │ ├── various_switching.c3t │ │ ├── while_statement_placement.c3 │ │ ├── while_statement_placement2.c3 │ │ └── while_switch.c3t │ ├── stdlib │ │ ├── ascii.c3 │ │ ├── map_linux.c3t │ │ ├── map_macos.c3t │ │ ├── memcomp.c3t │ │ ├── minmax.c3 │ │ ├── print_env_defines.c3 │ │ └── priorityqueue.c3t │ ├── strings │ │ ├── literal_errors.c3 │ │ ├── literal_hex_ok.c3 │ │ ├── literal_to_subarray.c3t │ │ ├── multiline_strings.c3t │ │ ├── string_escape.c3t │ │ ├── string_len.c3t │ │ └── string_to_array.c3t │ ├── struct │ │ ├── const_access_error.c3 │ │ ├── const_slice_struct.c3t │ │ ├── const_zero_init_1360.c3t │ │ ├── duplicate_member.c3 │ │ ├── flex_array_comparison.c3 │ │ ├── flex_array_struct_err.c3 │ │ ├── flexible_array_resolve.c3 │ │ ├── func_return_struct.c3 │ │ ├── init_cont_struct_array_locally.c3t │ │ ├── initialize_inline_designated.c3t │ │ ├── inline_array_access.c3t │ │ ├── inner_struct_name.c3 │ │ ├── member_access.c3 │ │ ├── member_expr.c3 │ │ ├── multi_member_attributes.c3t │ │ ├── nested_struct_init.c3t │ │ ├── nested_struct_union_init.c3t │ │ ├── recursive_structs.c3 │ │ ├── simple_struct.c3t │ │ ├── sret.c3t │ │ ├── struct_as_value.c3t │ │ ├── struct_as_value_aarch64.c3t │ │ ├── struct_bad_member.c3 │ │ ├── struct_codegen.c3t │ │ ├── struct_codegen_empty.c3t │ │ ├── struct_codegen_fam.c3t │ │ ├── struct_comma.c3 │ │ ├── struct_const_construct_simple.c3t │ │ ├── struct_nopadding_compact.c3t │ │ ├── struct_pack_and_align.c3t │ │ ├── struct_params.c3 │ │ ├── struct_reinit.c3t │ │ ├── struct_union_inner_align.c3t │ │ └── zero_member.c3 │ ├── switch │ │ ├── bad_ranges.c3 │ │ ├── enum_jump_switch_and_range.c3t │ │ ├── failable_switch.c3 │ │ ├── jump_bug_nested.c3t │ │ ├── jump_bugs.c3t │ │ ├── jump_with_inc.c3t │ │ ├── simple_jump.c3t │ │ └── switch_in_defer_macro.c3t │ ├── symbols │ │ ├── allow_local_shadowing.c3 │ │ ├── shadow_struct.c3 │ │ └── various.c3 │ ├── types │ │ ├── enum_illegal_type.c3 │ │ ├── enum_implicit_overflow.c3 │ │ ├── enum_inference.c3 │ │ ├── enum_ok.c3 │ │ ├── enum_param.c3 │ │ ├── enum_parse_errors.c3 │ │ ├── illegal_array_size_constant.c3 │ │ ├── non_rec_fn.c3 │ │ ├── recursive_array.c3 │ │ ├── recursive_fn.c3 │ │ ├── recursive_typedef.c3 │ │ ├── redefinition.c3 │ │ ├── typedefs.c3 │ │ └── various.c3 │ ├── unicode │ │ └── commenting-out.c3 │ ├── union │ │ ├── designated_union_zeroing.c3t │ │ ├── flexible_array_union.c3 │ │ ├── inferred_size_vector.c3 │ │ ├── test_unions.c3 │ │ ├── union_codegen_const.c3t │ │ ├── union_codegen_empty.c3t │ │ ├── union_codegen_overwrite_call.c3t │ │ ├── union_in_struct.c3t │ │ ├── union_member_voidcast.c3 │ │ └── union_zero.c3 │ ├── variables │ │ ├── const_in_func.c3t │ │ ├── consts.c3 │ │ ├── static_in_macro.c3t │ │ ├── var_init.c3t │ │ └── var_init_multi.c3t │ ├── vector │ │ ├── gather_scatter.c3t │ │ ├── swizzle_vector_ref.c3t │ │ ├── swizzling.c3 │ │ ├── vector_bit.c3t │ │ ├── vector_consts.c3t │ │ ├── vector_conversion_scalar.c3 │ │ ├── vector_incdec.c3t │ │ ├── vector_init.c3t │ │ ├── vector_init_regression.c3t │ │ ├── vector_lowering_regression1.c3t │ │ ├── vector_ops2.c3t │ │ ├── vector_param.c3t │ │ ├── vector_pointer_errors.c3 │ │ ├── vector_shift.c3t │ │ ├── vector_to_array_cast.c3t │ │ ├── vector_to_array_fail.c3 │ │ └── vector_to_vector_const_fail.c3 │ └── visibility │ │ ├── ambiguous_recursive.c3 │ │ ├── ambiguous_var.c3t │ │ ├── export_property.c3t │ │ ├── no_shared_imports.c3t │ │ ├── not_visible.c3t │ │ ├── private_import.c3 │ │ ├── private_import2.c3 │ │ ├── private_to_extern.c3t │ │ ├── shared_module.c3t │ │ └── simple_visibility.c3t ├── tmp │ └── .gitkeep └── unit │ ├── regression │ ├── any.c3 │ ├── bitstruct_ops.c3 │ ├── bitstruct_ops2.c3 │ ├── bitstruct_ops3.c3 │ ├── cast_slice_to_arr.c3 │ ├── castable_assignable.c3 │ ├── catch_err.c3 │ ├── copysign.c3 │ ├── ct_slice.c3 │ ├── distinct_inline.c3 │ ├── faults.c3 │ ├── file_line_func_module_builtins.c3 │ ├── gather_scatter.c3 │ ├── inc_dec.c3 │ ├── int128.c3 │ ├── int_min.c3 │ ├── liveness_any.c3 │ ├── lvalue_handling.c3 │ ├── masked_load_store.c3 │ ├── methodsof.c3 │ ├── pointer_diff.c3 │ ├── pointer_non_decay.c3 │ ├── select.c3 │ ├── signed_unsigned_compare.c3 │ ├── slice_assign.c3 │ ├── struct_alignment.c3 │ ├── subscripting.c3 │ ├── subtype.c3 │ ├── swizzle.c3 │ ├── ternary.c3 │ ├── unwrapping.c3 │ ├── vecpointer.c3 │ ├── vector_conversion.c3 │ ├── vector_method_reduce.c3 │ └── vector_ops.c3 │ └── stdlib │ ├── atomic.c3 │ ├── atomic_types.c3 │ ├── collections │ ├── bitset.c3 │ ├── copy_map.c3 │ ├── elastic_array.c3 │ ├── enummap.c3 │ ├── generic_list.c3 │ ├── linkedlist.c3 │ ├── list.c3 │ ├── map.c3 │ ├── object.c3 │ ├── priorityqueue.c3 │ ├── range.c3 │ └── ringbuffer.c3 │ ├── compression │ └── qoi.c3 │ ├── conv_tests.c3 │ ├── core │ ├── array.c3 │ ├── bitorder.c3 │ ├── builtintests.c3 │ ├── comparison.c3 │ ├── dstring.c3 │ ├── formatter.c3 │ ├── mem_allocator.c3 │ ├── runtime.c3 │ ├── string.c3 │ ├── string_iterator.c3 │ └── test_test.c3 │ ├── crypto │ └── rc4.c3 │ ├── encoding │ ├── base32.c3 │ ├── base64.c3 │ ├── csv.c3 │ ├── hex.c3 │ └── json.c3 │ ├── hash │ ├── fnv32a.c3 │ ├── fnv64a.c3 │ ├── md5.c3 │ ├── sha1.c3 │ └── sha256.c3 │ ├── io │ ├── bits.c3 │ ├── bufferstream.c3 │ ├── bytebuffer.c3 │ ├── bytestream.c3 │ ├── dstringstream.c3 │ ├── file_read_write_any.c3 │ ├── fileinfo.c3 │ ├── limitreader.c3 │ ├── multireader.c3 │ ├── multiwriter.c3 │ ├── path.c3 │ ├── printf.c3 │ ├── scanner.c3 │ ├── stream.c3 │ ├── teereader.c3 │ └── varint.c3 │ ├── macros │ └── core_builtins.c3 │ ├── math │ ├── bigint.c3 │ ├── frexp_signbit.c3 │ ├── math.c3 │ ├── math_complex.c3 │ ├── math_is_even_odd.c3 │ ├── matrix.c3 │ ├── quaternion.c3 │ └── random.c3 │ ├── mem │ └── temp_mem.c3 │ ├── net │ ├── inetaddr.c3 │ ├── url.c3 │ └── url_encoding.c3 │ ├── os │ └── env.c3 │ ├── sort │ ├── binarysearch.c3 │ ├── countingsort.c3 │ ├── insertionsort.c3 │ ├── quickselect.c3 │ ├── quicksort.c3 │ ├── sort.c3 │ └── sorted.c3 │ ├── string.c3 │ ├── string_to_float.c3 │ ├── threads │ ├── channel.c3 │ ├── mutex.c3 │ ├── pool.c3 │ └── simple_thread.c3 │ └── time │ ├── datetime.c3 │ ├── format.c3 │ └── time.c3 └── wrapper ├── include └── c3_llvm.h └── src └── wrapper.cpp /.editorconfig: -------------------------------------------------------------------------------- 1 | # EditorConfig is awesome: https://editorconfig.org 2 | 3 | root = true 4 | 5 | [*] 6 | charset = utf-8 7 | end_of_line = lf 8 | 9 | [CMakeLists.txt] 10 | indent_style = space 11 | indent_size = 4 12 | 13 | [*.{c,cc,h}] 14 | indent_style = tab 15 | 16 | [*.{c3}] 17 | indent_style = tab 18 | 19 | [*.{json,toml,yml,gyp}] 20 | indent_style = space 21 | indent_size = 2 22 | 23 | [*.{py,pyi}] 24 | indent_style = tab 25 | 26 | -------------------------------------------------------------------------------- /.gitattributes: -------------------------------------------------------------------------------- 1 | $ cat .gitattributes 2 | * text=auto 3 | -------------------------------------------------------------------------------- /.gitmodules: -------------------------------------------------------------------------------- 1 | [submodule "tilde-backend"] 2 | path = tilde-backend 3 | url = https://github.com/c3lang/tilde-backend 4 | -------------------------------------------------------------------------------- /lib/std/collections/tuple.c3: -------------------------------------------------------------------------------- 1 | module std::collections::tuple(); 2 | 3 | struct Tuple 4 | { 5 | Type1 first; 6 | Type2 second; 7 | } 8 | 9 | module std::collections::triple(); 10 | 11 | struct Triple 12 | { 13 | Type1 first; 14 | Type2 second; 15 | Type3 third; 16 | } -------------------------------------------------------------------------------- /lib/std/crypto/crypto.c3: -------------------------------------------------------------------------------- 1 | module std::crypto; 2 | 3 | fn bool safe_compare(void* data1, void* data2, usz len) 4 | { 5 | char match = 0; 6 | for (usz i = 0; i < len; i++) 7 | { 8 | match = match | (mem::@volatile_load(((char*)data1)[i]) ^ mem::@volatile_load(((char*)data2)[i])); 9 | } 10 | return match == 0; 11 | } 12 | 13 | -------------------------------------------------------------------------------- /lib/std/crypto/dh.c3: -------------------------------------------------------------------------------- 1 | module std::crypto::dh; 2 | import std::math::bigint; 3 | 4 | fn BigInt generate_secret(BigInt p, BigInt x, BigInt y) 5 | { 6 | return y.mod_pow(x, p); 7 | } 8 | 9 | fn BigInt public_key(BigInt p, BigInt g, BigInt x) 10 | { 11 | return g.mod_pow(x, p); 12 | } 13 | -------------------------------------------------------------------------------- /lib/std/encoding/encoding.c3: -------------------------------------------------------------------------------- 1 | module std::encoding; 2 | 3 | fault DecodingFailure 4 | { 5 | INVALID_CHARACTER, 6 | INVALID_PADDING, 7 | } -------------------------------------------------------------------------------- /lib/std/math/math_nolibc/fabs.c3: -------------------------------------------------------------------------------- 1 | module std::math::nolibc @if(env::NO_LIBC || $feature(C3_MATH)); 2 | 3 | fn double _fabs(double x) @weak @extern("fabs") @nostrip 4 | { 5 | ulong ix = bitcast(x, ulong); 6 | ix &= ~(1ul << 63); 7 | return bitcast(ix, double); 8 | } 9 | 10 | fn float _fabsf(float x) @weak @extern("fabsf") @nostrip 11 | { 12 | uint ix = bitcast(x, uint); 13 | ix &= 0x7fffffff; 14 | return bitcast(ix, float); 15 | } 16 | -------------------------------------------------------------------------------- /lib/std/math/math_nolibc/trig.c3: -------------------------------------------------------------------------------- 1 | module std::math::nolibc @if(env::NO_LIBC || $feature(C3_MATH)); 2 | 3 | fn double sincos_broken(double x) @extern("sincos") @weak @nostrip 4 | { 5 | unreachable("'sinccos' not supported"); 6 | } 7 | 8 | 9 | -------------------------------------------------------------------------------- /lib/std/os/linux/heap.c3: -------------------------------------------------------------------------------- 1 | module std::os::linux @if(env::LINUX); 2 | extern fn usz malloc_usable_size(void* ptr); -------------------------------------------------------------------------------- /lib/std/os/macos/cocoa.c3: -------------------------------------------------------------------------------- 1 | module std::os::darwin::cocoa @if(env::OS_TYPE == MACOS) @link("Cocoa.framework"); 2 | 3 | extern fn int nsApplicationMain(int argc, char **argv) @extern("NSApplicationMain"); 4 | -------------------------------------------------------------------------------- /lib/std/os/macos/core_foundation.c3: -------------------------------------------------------------------------------- 1 | module std::os::macos::cf @if(env::DARWIN) @link(env::DARWIN, "CoreFoundation.framework"); 2 | 3 | distinct CFTypeRef = void*; 4 | def CFIndex = isz; 5 | struct CFRange 6 | { 7 | CFIndex location; 8 | CFIndex length; 9 | } 10 | 11 | extern fn CFTypeRef macos_CFRetain(CFTypeRef cf) @extern("CFRetain") @builtin; 12 | extern fn void macos_CFRelease(CFTypeRef cf) @extern("CFRelease") @builtin; -------------------------------------------------------------------------------- /lib/std/os/macos/heap.c3: -------------------------------------------------------------------------------- 1 | module std::os::darwin @if(env::DARWIN); 2 | 3 | extern fn usz malloc_size(void* ptr); 4 | -------------------------------------------------------------------------------- /lib/std/os/posix/general.c3: -------------------------------------------------------------------------------- 1 | module std::os::posix; 2 | 3 | extern ZString* environ; 4 | 5 | -------------------------------------------------------------------------------- /lib/std/os/posix/heap.c3: -------------------------------------------------------------------------------- 1 | module std::os::posix @if(env::POSIX); 2 | 3 | extern fn CInt posix_memalign(void **memptr, usz alignment, usz size); -------------------------------------------------------------------------------- /lib/std/os/win32/gdi.c3: -------------------------------------------------------------------------------- 1 | module std::os::win32 @if(env::WIN32); 2 | 3 | extern fn Win32_HBRUSH createSolidBrush(Win32_COLORREF) @extern("CreateSolidBrush"); 4 | extern fn Win32_COLORREF setTextColor(Win32_HDC, Win32_COLORREF) @extern("SetTextColor"); 5 | extern fn CInt setBkMode(Win32_HDC, CInt) @extern("SetBkMode"); 6 | extern fn Win32_BOOL textOut(Win32_HDC, CInt, CInt, Win32_LPCWSTR, CInt) @extern("TextOutW"); -------------------------------------------------------------------------------- /lib/std/threads/os/thread_none.c3: -------------------------------------------------------------------------------- 1 | module std::thread::os @if (!env::POSIX && !env::WIN32); 2 | 3 | distinct NativeMutex = int; 4 | distinct NativeConditionVariable = int; 5 | distinct NativeOnceFlag = int; 6 | distinct NativeThread = int; -------------------------------------------------------------------------------- /lib/std/time/clock.c3: -------------------------------------------------------------------------------- 1 | module std::time::clock; 2 | import std::time::os; 3 | 4 | fn Clock now() 5 | { 6 | $if $defined(os::native_clock): 7 | return os::native_clock(); 8 | $else 9 | unreachable("Clock unsupported"); 10 | $endif 11 | } 12 | 13 | fn NanoDuration Clock.mark(&self) 14 | { 15 | Clock mark = now(); 16 | NanoDuration diff = (NanoDuration)(mark - *self); 17 | *self = mark; 18 | return diff; 19 | } 20 | 21 | fn NanoDuration Clock.to_now(self) 22 | { 23 | return (NanoDuration)(now() - self); 24 | } -------------------------------------------------------------------------------- /nix/shell.nix: -------------------------------------------------------------------------------- 1 | { 2 | lib, 3 | mkShell, 4 | clang-tools, 5 | c3c, 6 | }: 7 | mkShell.override { 8 | inherit (c3c) stdenv; 9 | } { 10 | name = "c3c-shell"; 11 | 12 | inputsFrom = [ 13 | c3c 14 | ]; 15 | 16 | packages = [ 17 | clang-tools 18 | ]; 19 | 20 | # Usage: 'cmake . -Bbuild $C3_CMAKE_FLAGS' or 'cmake . -Bbuild $=C3_CMAKE_FLAGS' on zsh 21 | C3_CMAKE_FLAGS = lib.concatStringsSep " " c3c.cmakeFlags; 22 | } 23 | -------------------------------------------------------------------------------- /resources/examples/args.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | fn void main(String[] args) 4 | { 5 | io::printn(args); 6 | } 7 | -------------------------------------------------------------------------------- /resources/examples/constants.c3: -------------------------------------------------------------------------------- 1 | const char AA @private = 1; 2 | const char BB = 200 ; 3 | const uint CC @private = ~(uint)(0); 4 | const FOO @private = ~(uint)(0); 5 | -------------------------------------------------------------------------------- /resources/examples/dynlib-test/add.c3: -------------------------------------------------------------------------------- 1 | import std; 2 | struct Foo(Printable) 3 | { 4 | int a; 5 | } 6 | 7 | fn usz! Foo.to_format(&self, Formatter* f) @dynamic 8 | { 9 | return f.printf("Foo[%d]", self.a); 10 | } 11 | 12 | fn int add(int a, int b) @export("adder") 13 | { 14 | io::printn("In adder"); 15 | Foo x = { a }; 16 | io::printfn("Print foo: %s", x); 17 | return a + b; 18 | } -------------------------------------------------------------------------------- /resources/examples/dynlib-test/test.c: -------------------------------------------------------------------------------- 1 | #include 2 | extern int adder(int a, int b); 3 | 4 | int main() 5 | { 6 | printf("%d\n", adder(1, 4)); 7 | return 0; 8 | } -------------------------------------------------------------------------------- /resources/examples/dynlib-test/test.c3: -------------------------------------------------------------------------------- 1 | import std; 2 | extern fn int adder(int a, int b); 3 | 4 | fn int main() 5 | { 6 | io::printn(adder(1, 4)); 7 | return 0; 8 | } -------------------------------------------------------------------------------- /resources/examples/embedded/riscv-qemu/README.md: -------------------------------------------------------------------------------- 1 | # Risc-V 32 Embedded Example With QEMU 2 | ## Prereqs 3 | - QEMU 4 | - Risc-V toolchain 5 | - C3C 6 | - Make 7 | ## Running 8 | `make run` 9 | -------------------------------------------------------------------------------- /resources/examples/embedded/riscv-qemu/baremetal.ld: -------------------------------------------------------------------------------- 1 | EXTERN(main) 2 | 3 | SECTIONS 4 | { 5 | . = 0x80000000; /* QEMU default load address to run bios */ 6 | .text : { 7 | KEEP(*(.text._start)); /* Ensure _start is placed first */ 8 | *(.text*); /* Program code here */ 9 | } 10 | . = ALIGN (CONSTANT (COMMONPAGESIZE)); /* Make sure linker does not jam data into text section, making text writable */ 11 | .data : { 12 | *(.data*) /* Stack goes here */ 13 | } 14 | } -------------------------------------------------------------------------------- /resources/examples/embedded/riscv-qemu/hello.c3: -------------------------------------------------------------------------------- 1 | import uart; 2 | import semihost; 3 | 4 | const UART0_BASE = 0x10000000; 5 | 6 | fn void main() @export("main") { 7 | Uart* uart0 = (Uart*)UART0_BASE; // Create pointer to UART 0 8 | uart0.fcr = uart::UARTFCR_FFENA; // Enable FIFO 9 | uart0.puts("Hello World!\n"); // Write the string to the UART 10 | semihost::exit(0); // Semihosting call to exit host 11 | } 12 | -------------------------------------------------------------------------------- /resources/examples/factorial_macro.c3: -------------------------------------------------------------------------------- 1 | macro int factorial($n) 2 | { 3 | $if $n == 0: 4 | return 1; 5 | $else 6 | return $n * factorial($n - 1); 7 | $endif 8 | } 9 | 10 | extern fn void printf(char *fmt, ...); 11 | 12 | fn void main() 13 | { 14 | int x = factorial(12); 15 | printf("12! = %d\n", x); 16 | } -------------------------------------------------------------------------------- /resources/examples/hello_world.txt: -------------------------------------------------------------------------------- 1 | Hello, world! 2 | ¡Hola Mundo! 3 | Γειά σου Κόσμε! 4 | Привет, мир! 5 | こんにちは世界! 6 | 你好世界! 7 | नमस्ते दुनिया! 8 | 👋🌎! -------------------------------------------------------------------------------- /resources/examples/hello_world_many.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | fn void main() 4 | { 5 | String[] greetings = { 6 | "Hello, world!", 7 | "¡Hola Mundo!", 8 | "Γειά σου Κόσμε!", 9 | "Привет, мир!", 10 | "こんにちは世界!", 11 | "你好世界!", 12 | "नमस्ते दुनिया!", 13 | "👋🌎!" 14 | }; 15 | foreach (greeting : greetings) 16 | { 17 | io::printn(greeting); 18 | } 19 | } -------------------------------------------------------------------------------- /resources/examples/load_world.c3: -------------------------------------------------------------------------------- 1 | module load_world; 2 | import std::io; 3 | fn void main() 4 | { 5 | File f = file::open("examples/hello_world.txt", "rb")!!; 6 | defer f.close()!!; 7 | while (!f.eof()) 8 | { 9 | @pool() { io::printn(io::treadline(&f)!!); }; 10 | } 11 | } -------------------------------------------------------------------------------- /resources/examples/ls.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | fn void main() 4 | { 5 | Path path = path::new_cwd()!!; 6 | foreach (i, p : path::new_ls(path)!!) 7 | { 8 | io::printfn("%02d %s", i, p.str_view()); 9 | } 10 | } -------------------------------------------------------------------------------- /resources/examples/opengl/LICENSE: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tsoding/c3c/3a502feb1db16e1b047d1165baf4635149385182/resources/examples/opengl/LICENSE -------------------------------------------------------------------------------- /resources/examples/opengl/README.md: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tsoding/c3c/3a502feb1db16e1b047d1165baf4635149385182/resources/examples/opengl/README.md -------------------------------------------------------------------------------- /resources/examples/opengl/docs/.gitkeep: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tsoding/c3c/3a502feb1db16e1b047d1165baf4635149385182/resources/examples/opengl/docs/.gitkeep -------------------------------------------------------------------------------- /resources/examples/opengl/lib/.gitkeep: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tsoding/c3c/3a502feb1db16e1b047d1165baf4635149385182/resources/examples/opengl/lib/.gitkeep -------------------------------------------------------------------------------- /resources/examples/opengl/resources/.gitkeep: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tsoding/c3c/3a502feb1db16e1b047d1165baf4635149385182/resources/examples/opengl/resources/.gitkeep -------------------------------------------------------------------------------- /resources/examples/opengl/scripts/.gitkeep: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tsoding/c3c/3a502feb1db16e1b047d1165baf4635149385182/resources/examples/opengl/scripts/.gitkeep -------------------------------------------------------------------------------- /resources/examples/opengl/test/.gitkeep: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tsoding/c3c/3a502feb1db16e1b047d1165baf4635149385182/resources/examples/opengl/test/.gitkeep -------------------------------------------------------------------------------- /resources/examples/process.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::os::process; 3 | import std::io; 4 | 5 | fn void main() 6 | { 7 | String command = env::WIN32 ? "dir" : "ls"; 8 | SubProcess x = process::create({ command }, { .search_user_path = true })!!; 9 | x.join()!!; 10 | InStream stream = &&x.stdout(); 11 | while (try char b = stream.read_byte()) 12 | { 13 | io::printf("%c", b); 14 | } 15 | io::printn("...Done"); 16 | } 17 | -------------------------------------------------------------------------------- /resources/examples/stacktrace_example.c3: -------------------------------------------------------------------------------- 1 | fn void main() { 2 | foo(); 3 | } 4 | 5 | fn void foo() { 6 | bar(); 7 | } 8 | 9 | macro bar() { 10 | unreachable(); 11 | } 12 | -------------------------------------------------------------------------------- /resources/examples/staticlib-test/add.c3: -------------------------------------------------------------------------------- 1 | module add; 2 | import std; 3 | struct Foo(Printable) 4 | { 5 | int a; 6 | } 7 | 8 | fn usz! Foo.to_format(&self, Formatter* f) @dynamic 9 | { 10 | return f.printf("Foo[%d]", self.a); 11 | } 12 | 13 | fn int add(int a, int b) @export("adder") 14 | { 15 | io::printn("In adder"); 16 | Foo x = { a }; 17 | io::printfn("Print foo: %s", x); 18 | return a + b; 19 | } -------------------------------------------------------------------------------- /resources/examples/staticlib-test/test.c: -------------------------------------------------------------------------------- 1 | #include 2 | extern int adder(int a, int b); 3 | 4 | int main() 5 | { 6 | printf("%d\n", adder(1, 4)); 7 | return 0; 8 | } -------------------------------------------------------------------------------- /resources/examples/staticlib-test/test.c3: -------------------------------------------------------------------------------- 1 | module add; 2 | import std; 3 | extern fn int adder(int a, int b); 4 | 5 | fn int main() 6 | { 7 | io::printn(adder(1, 4)); 8 | return 0; 9 | } -------------------------------------------------------------------------------- /resources/examples/swap.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::io; 3 | 4 | <* 5 | @require $defined(#a = #b, #b = #a) 6 | *> 7 | macro void @swap(#a, #b) 8 | { 9 | var temp = #a; 10 | #a = #b; 11 | #b = temp; 12 | } 13 | 14 | fn void main() 15 | { 16 | int x = 123; 17 | int y = 456; 18 | @swap(x, y); 19 | io::printfn("x: %d y: %d", x, y); 20 | } -------------------------------------------------------------------------------- /resources/examples/timeit.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::time; 3 | import std::io; 4 | 5 | def foo = write; 6 | 7 | def Int = int; 8 | 9 | macro @timeit(#call) 10 | { 11 | Clock t = clock::now(); 12 | var result = #call; 13 | io::printfn("'%s' took %d ns", $stringify(#call), t.mark()); 14 | return result; 15 | } 16 | 17 | fn int write() 18 | { 19 | for (int i = 0; i < 1000; i++) io::printf("%d", i); 20 | io::printn(); 21 | return 0; 22 | } 23 | 24 | fn void main() 25 | { 26 | @timeit(write()); 27 | } -------------------------------------------------------------------------------- /resources/grammar/Makefile: -------------------------------------------------------------------------------- 1 | c3yacc: grammar.y c3.l 2 | flex --header-file=lex.yy.h -8 c3.l 3 | bison -d grammar.y; 4 | cc -O2 -o c3yacc lex.yy.c grammar.tab.c 5 | 6 | clean: 7 | rm -f c3yacc grammar.output *.o grammar.tab.* lex.yy.* -------------------------------------------------------------------------------- /resources/grammar/check_grammar.sh: -------------------------------------------------------------------------------- 1 | for fn in `find ../../../c3c -name '*.c3' | sort` 2 | do 3 | echo -n $fn 4 | cat $fn | ./c3yacc 5 | done 6 | -------------------------------------------------------------------------------- /resources/images/vkQuake.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tsoding/c3c/3a502feb1db16e1b047d1165baf4635149385182/resources/images/vkQuake.png -------------------------------------------------------------------------------- /resources/linux_stack.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::io; 3 | import std::collections::map; 4 | import std::os; 5 | 6 | fn void! test2() 7 | { 8 | builtin::print_backtrace("hello", 1); 9 | } 10 | 11 | fn void test1() 12 | { 13 | (void)test2(); 14 | } 15 | 16 | 17 | fn void foo() 18 | { 19 | baz(); 20 | } 21 | 22 | macro bar() 23 | { 24 | builtin::print_backtrace("bar", 1); 25 | } 26 | 27 | macro baz() 28 | { 29 | bar(); 30 | } 31 | 32 | 33 | fn void main() 34 | { 35 | test1(); 36 | foo(); 37 | } -------------------------------------------------------------------------------- /resources/msvc_stack.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::io; 3 | import std::collections::map; 4 | import std::os; 5 | import libc; 6 | 7 | fn void bye() @finalizer 8 | { 9 | libc::puts("Bye from finalizer!"); 10 | } 11 | 12 | fn void test1() 13 | { 14 | builtin::print_backtrace("hello", 1); 15 | 16 | 17 | int x = 1; 18 | return; 19 | } 20 | 21 | fn void main() 22 | { 23 | test1(); 24 | } -------------------------------------------------------------------------------- /resources/rosettacode/helloworld.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | fn int main() 4 | { 5 | io::printn("Hello world"); 6 | return 0; 7 | } -------------------------------------------------------------------------------- /resources/rosettacode/quine.c3: -------------------------------------------------------------------------------- 1 | import std::io; fn void main() => io::printfn("%sString q = \x60%s\x60;", q, q);String q = `import std::io; fn void main() => io::printfn("%sString q = \x60%s\x60;", q, q);`; -------------------------------------------------------------------------------- /resources/testfragments/diagnostic.c3: -------------------------------------------------------------------------------- 1 | import std; 2 | struct Overalign 3 | { 4 | double[<33>] x; 5 | } 6 | 7 | def Olist = List(); 8 | 9 | fn void main() 10 | { 11 | Olist l; 12 | Overalign y; 13 | for (int i = 0; i < 1000; i++) 14 | { 15 | io::printfn("Pushing %d", i); 16 | l.push(y); 17 | if (i > 3) io::printfn("Diff %d", (usz)l.get_ref(i) - (usz)l.get_ref(i - (usz)1)); 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /resources/testfragments/helloworld.c3: -------------------------------------------------------------------------------- 1 | module helloworld; 2 | import std::io; 3 | 4 | fn void main() 5 | { 6 | io::printn("Hello, World!"); 7 | } -------------------------------------------------------------------------------- /resources/testfragments/pwd2.c3: -------------------------------------------------------------------------------- 1 | module pwd; 2 | 3 | fn int getnum() => 3; -------------------------------------------------------------------------------- /resources/testfragments/test.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | extern fn int printf(char* message, ...); 4 | 5 | macro void @swap(&a, &b) 6 | { 7 | $typeof(*a) temp = *a; 8 | *a = *b; 9 | *b = temp; 10 | } 11 | 12 | fn void main() 13 | { 14 | int x = 1; 15 | int y = 2; 16 | @swap(x, y); 17 | printf("x: %d y: %d\n", x, y); 18 | } -------------------------------------------------------------------------------- /resources/testproject/csource/test.c: -------------------------------------------------------------------------------- 1 | int test_doubler(int d) 2 | { 3 | return d * d; 4 | } -------------------------------------------------------------------------------- /resources/testproject/lib/clib.c3l/clib.c3i: -------------------------------------------------------------------------------- 1 | module clib; 2 | 3 | extern fn void hello_from_c(); 4 | -------------------------------------------------------------------------------- /resources/testproject/lib/clib.c3l/hello2.c: -------------------------------------------------------------------------------- 1 | #include 2 | void hello_from_c(void) 3 | { 4 | puts("Hello from C!"); 5 | } -------------------------------------------------------------------------------- /resources/testproject/lib/clib.c3l/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "provides" : "clib", 3 | "c-sources" : ["hello2.c", "whitespace test.c"], 4 | "targets" : { 5 | "macos-x64" : { 6 | }, 7 | "macos-aarch64" : {}, 8 | "linux-x64" : { 9 | "cflags": "-fPIE" 10 | }, 11 | "windows-x64" : { 12 | "c-include-dirs": ["C:\\"] 13 | } 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /resources/testproject/lib/clib.c3l/whitespace test.c: -------------------------------------------------------------------------------- 1 | #include 2 | -------------------------------------------------------------------------------- /resources/testproject/lib/clib2.c3l: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tsoding/c3c/3a502feb1db16e1b047d1165baf4635149385182/resources/testproject/lib/clib2.c3l -------------------------------------------------------------------------------- /resources/testproject/scripts/scriptme.c3: -------------------------------------------------------------------------------- 1 | import std; 2 | fn int main(String[] args) 3 | { 4 | if (args.len == 1) return 1; 5 | io::printn("Hello from script!"); 6 | return 0; 7 | } -------------------------------------------------------------------------------- /resources/testproject/scripts/scripts.md: -------------------------------------------------------------------------------- 1 | `$exec` are by default run here. -------------------------------------------------------------------------------- /resources/testproject/src/bar.c3: -------------------------------------------------------------------------------- 1 | module bar; 2 | 3 | import baz::foo; 4 | import testbaz::zab; 5 | 6 | fn void test() 7 | { 8 | Foo x; 9 | baz::foo::test(); 10 | foo::test(); 11 | baz::foo::Foo y; 12 | foo::Foo d; 13 | Zab z; 14 | } 15 | -------------------------------------------------------------------------------- /resources/testproject/src/foo.c3: -------------------------------------------------------------------------------- 1 | module baz::foo; 2 | 3 | import bar; 4 | 5 | struct Foo 6 | { 7 | int a; 8 | } 9 | 10 | extern fn void printf(char *hello); 11 | 12 | fn void ofke() @private 13 | {} 14 | 15 | fn void exple() @private{} 16 | 17 | fn void test() 18 | { 19 | printf("Hello from baz::foo::test()!\n"); 20 | } -------------------------------------------------------------------------------- /resources/testproject/src/zab.c3: -------------------------------------------------------------------------------- 1 | module testbaz::zab; 2 | 3 | struct Zab 4 | { 5 | double a; 6 | } 7 | -------------------------------------------------------------------------------- /src/build/project.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | #include "../utils/json.h" 3 | 4 | const char** get_project_dependency_directories(); 5 | const char** get_project_dependencies(); 6 | 7 | static void print_vec(const char *header, const char **vec, bool opt, const char *delim); 8 | 9 | void add_libraries_to_project_file(const char** libs, const char* target_name); 10 | 11 | const char* vendor_fetch_single(const char* lib, const char* path); 12 | -------------------------------------------------------------------------------- /src/compiler/c_codegen_internal.h: -------------------------------------------------------------------------------- 1 | #include "codegen_internal.h" 2 | -------------------------------------------------------------------------------- /src/compiler/subprocess.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | int run_subprocess(const char *name, const char **args); 4 | -------------------------------------------------------------------------------- /src/compiler_tests/tests.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | // Copyright (c) 2019 Christoffer Lerno. All rights reserved. 4 | // Use of this source code is governed by the GNU LGPLv3.0 license 5 | // a copy of which can be found in the LICENSE file. 6 | 7 | 8 | void compiler_tests(void); 9 | -------------------------------------------------------------------------------- /src/utils/hostinfo.h: -------------------------------------------------------------------------------- 1 | #if !defined(HOSTINFO_H) && !LLVM_AVAILABLE 2 | #define HOSTINFO_H 3 | 4 | void hostinfo_x86_features(X86Features *cpu_features); 5 | ArchType hostinfo_arch_type(void); 6 | EnvironmentType hostinfo_env_type(void); 7 | OsType hostinfo_os_type(void); 8 | VendorType hostinfo_vendor_type(void); 9 | const char * hostinfo_default_triple(void); 10 | const char * hostinfo_x86_cpu_name(void); // for example: "x86-64", "x86-64-v4" 11 | 12 | #endif 13 | -------------------------------------------------------------------------------- /src/utils/whereami.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | // Copyright (c) 2020 Christoffer Lerno. All rights reserved. 4 | // Use of this source code is governed by a LGPLv3.0 5 | // a copy of which can be found in the LICENSE file. 6 | 7 | char *find_executable_path(void); 8 | -------------------------------------------------------------------------------- /src/version.h: -------------------------------------------------------------------------------- 1 | #define COMPILER_VERSION "0.6.7" 2 | #define PRERELEASE 1 3 | #define ALLOW_DEPRECATED_6 1 -------------------------------------------------------------------------------- /test/test_suite/abi/darwin64_sret.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module foo; 3 | 4 | struct SimdDouble4x4 5 | { 6 | double[<4>][4] columns; 7 | } 8 | 9 | fn SimdDouble4x4 ident(SimdDouble4x4 x) { 10 | return x; 11 | } 12 | 13 | /* #expect: foo.ll 14 | 15 | define void @foo.ident(ptr noalias sret(%SimdDouble4x4) align 32 %0, ptr byval(%SimdDouble4x4) align 32 %1) #0 { 16 | entry: 17 | call void @llvm.memcpy.p0.p0.i32(ptr align 32 %0, ptr align 32 %1, i32 128, i1 false) 18 | ret void 19 | } -------------------------------------------------------------------------------- /test/test_suite/abi/darwin_arg.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | struct Str 4 | { 5 | union 6 | { 7 | float128 a; 8 | long c; 9 | } 10 | } 11 | 12 | extern fn void d(Str s); 13 | Str ss; 14 | fn void f9122143() 15 | { 16 | d(ss); 17 | } 18 | 19 | /* #expect: test.ll 20 | 21 | declare void @d(i64, double) #0 22 | 23 | %lo = load i64, ptr @test.ss, align 16 24 | %hi = load double, ptr getelementptr inbounds (i8, ptr @test.ss, i64 8), align 8 25 | call void @d(i64 %lo, double %hi) 26 | -------------------------------------------------------------------------------- /test/test_suite/abi/linking_extern.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module abc; 3 | extern fn void puts(char*); 4 | macro void test() 5 | { 6 | puts("b"); 7 | } 8 | module test; 9 | import abc; 10 | extern fn void puts(char*); 11 | fn void main() 12 | { 13 | puts("a"); 14 | abc::test(); 15 | } 16 | 17 | /* #expect: test.ll 18 | 19 | define void @test.main() #0 { 20 | entry: 21 | call void @puts(ptr @.str) 22 | call void @puts(ptr @.str.1) 23 | ret void 24 | } 25 | -------------------------------------------------------------------------------- /test/test_suite/abi/macho_section.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | 4 | int z @section("__TEXT,__custoection"); 5 | int w @section("__TEXT,__custoection"); 6 | 7 | fn void main() 8 | { 9 | int a = z + w; 10 | } 11 | 12 | /* #expect: test.ll 13 | 14 | @test.z = local_unnamed_addr global i32 0, section "__TEXT,__custoection", align 4 15 | @test.w = local_unnamed_addr global i32 0, section "__TEXT,__custoection", align 4 16 | -------------------------------------------------------------------------------- /test/test_suite/any/generic_interface.c3: -------------------------------------------------------------------------------- 1 | module foo(); 2 | 3 | interface Baz 4 | {} 5 | 6 | module test; 7 | import foo; 8 | 9 | fn void main() 10 | { 11 | Baz() x; 12 | } 13 | -------------------------------------------------------------------------------- /test/test_suite/any/interface_no_fn.c3: -------------------------------------------------------------------------------- 1 | interface IOp { 2 | int val; // #error: Interfaces can only have function 3 | int my_fn(); // missing fn 4 | } -------------------------------------------------------------------------------- /test/test_suite/any/interface_no_method_body_1536.c3: -------------------------------------------------------------------------------- 1 | interface Foo 2 | { 3 | fn int bar() 4 | { // #error: An interface method 5 | return 0; 6 | } 7 | } -------------------------------------------------------------------------------- /test/test_suite/any/interface_ptr.c3: -------------------------------------------------------------------------------- 1 | interface Abc {} 2 | 3 | fn void main() 4 | { 5 | Abc y; 6 | typeid z = y.type; 7 | void* x = y.ptr; 8 | } 9 | -------------------------------------------------------------------------------- /test/test_suite/arrays/array_indexing.c3: -------------------------------------------------------------------------------- 1 | enum Foo : int 2 | { 3 | TEST 4 | } 5 | 6 | int[100] a = { [Foo.TEST.ordinal] = 123 }; 7 | 8 | fn void test() 9 | { 10 | a[Foo.TEST.ordinal] = 33; 11 | } -------------------------------------------------------------------------------- /test/test_suite/arrays/array_invalid_casts.c3: -------------------------------------------------------------------------------- 1 | 2 | fn void test() 3 | { 4 | int[3] x; 5 | double *y = &x; // #error: 'int[3]*' to 'double* 6 | } 7 | 8 | fn void test2() 9 | { 10 | int[3] x; 11 | double[] z = &x; // #error: 'int[3]*' to 'double[]' 12 | } -------------------------------------------------------------------------------- /test/test_suite/arrays/array_struct.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | 4 | struct Foo 5 | { 6 | int x, y; 7 | } 8 | 9 | Foo[10] array @private; 10 | 11 | /* #expect: test.ll 12 | 13 | @test.array = internal unnamed_addr global [10 x %Foo] zeroinitializer, align 16 -------------------------------------------------------------------------------- /test/test_suite/arrays/global_array_non_const.c3: -------------------------------------------------------------------------------- 1 | 2 | const int CONSTANT = 1; 3 | int[CONSTANT] a2; 4 | int[3] a3 = { [CONSTANT] = 1 }; 5 | const bool B = true; 6 | int[B] c2; // #error: be implicitly converted 7 | 8 | int non_constant = 10; 9 | int[non_constant] b; // #error: Expected a constant value as 10 | 11 | fn int foo() 12 | { 13 | return 10; 14 | } 15 | 16 | int[foo()] c; // #error: Expected a constant value as 17 | 18 | -------------------------------------------------------------------------------- /test/test_suite/arrays/global_init_array_out_of_range.c3: -------------------------------------------------------------------------------- 1 | int[3] abc; 2 | int *bf3 = (&abc[4]) + 2; // #error: An index of '4' is out of range, a value between 0 and 2 was expected -------------------------------------------------------------------------------- /test/test_suite/arrays/inferred_array_err.c3: -------------------------------------------------------------------------------- 1 | fn int[?] hello() // #error: Inferred array types can only be used in declarations with initializers 2 | { 3 | return int[3] { 1, 2, 3}; 4 | } 5 | 6 | int[?] c; // #error: Inferred array types can only be used in declarations with initializers 7 | 8 | -------------------------------------------------------------------------------- /test/test_suite/arrays/inferred_array_err2.c3: -------------------------------------------------------------------------------- 1 | fn void test() 2 | { 3 | int[3] z; 4 | (int[?])(z); 5 | } -------------------------------------------------------------------------------- /test/test_suite/arrays/inferred_subarray.c3: -------------------------------------------------------------------------------- 1 | fn void main() 2 | { 3 | int[?][?][] x = int[2][1][] { { { 1, 2 } } }; 4 | int[?][?][?] y = int[2][1][] { { { 1, 2 } } }; 5 | } 6 | -------------------------------------------------------------------------------- /test/test_suite/arrays/negative_array.c3: -------------------------------------------------------------------------------- 1 | 2 | int[-1] a; // #error: An array may not have a negative 3 | int[10-20] b; // #error: An array may not have a negative 4 | int[<-1>] c; // #error: A vector may not have a negative width 5 | int[<10-20>] d; // #error: A vector may not have a negative width 6 | -------------------------------------------------------------------------------- /test/test_suite/arrays/slice.c3: -------------------------------------------------------------------------------- 1 | fn void test() 2 | { 3 | int[3] x = { 1, 2, 3 }; 4 | int[] z = &x; 5 | z[1]; 6 | // z.size(); 7 | } -------------------------------------------------------------------------------- /test/test_suite/asm/asm_bit_rv.c3t: -------------------------------------------------------------------------------- 1 | // #target: elf-riscv32 2 | module test; 3 | 4 | fn void main(String[] args) 5 | { 6 | asm 7 | { 8 | and $t0, $t1, $t2; 9 | or $a0, $a1, $a2; 10 | xor $s7, $s6, $s5; 11 | andi $s1, $s2, -2048; 12 | ori $s3, $s4, 2047; 13 | xori $t3, $t4, 1; 14 | not $t3, $t4; 15 | } 16 | } 17 | 18 | /* #expect: test.ll 19 | 20 | "and t0, t1, t2\0Aor a0, a1, a2\0Axor s7, s6, s5\0Aandi s1, s2, -2048\0Aori s3, s4, 2047\0Axori t3, t4, 1\0Anot t3, t4\0A", "~{x5},~{x9},~{x10},~{x19},~{x23},~{x28}"() -------------------------------------------------------------------------------- /test/test_suite/asm/asm_intr_rv.c3t: -------------------------------------------------------------------------------- 1 | // #target: elf-riscv32 2 | module test; 3 | 4 | fn void main(String[] args) 5 | { 6 | int x = 0; 7 | void* fp; 8 | asm 9 | { 10 | csrw $mstatus, $a0; 11 | csrrsi $zero, $mstatus, 8u; 12 | csrrci $zero, $mstatus, 31u; 13 | csrrw $zero, $mtvec, fp; 14 | mret; 15 | wfi; 16 | } 17 | } 18 | 19 | /* #expect: test.ll 20 | 21 | "csrw mstatus, a0\0Acsrrsi zero, mstatus, 8\0Acsrrci zero, mstatus, 31\0Acsrrw zero, mtvec, $0\0Amret \0Awfi \0A", "r,~{x0},~{mstatus},~{mtvec}"(ptr %1) -------------------------------------------------------------------------------- /test/test_suite/asm/asm_load_rv.c3t: -------------------------------------------------------------------------------- 1 | // #target: elf-riscv32 2 | module test; 3 | 4 | fn void main(String[] args) 5 | { 6 | int x = 2; 7 | asm 8 | { 9 | li $s1, -2147483648; 10 | lui $t0, 123456u; 11 | auipc $x15, 123456u; 12 | auipc $a0, 1; 13 | mv $a0, $a1; 14 | lw $a4, [&x]; 15 | lb $a5, [$a7 - 4]; 16 | } 17 | } 18 | 19 | /* #expect: test.ll 20 | 21 | "li s1, -2147483648\0Alui t0, 123456\0Aauipc x15, 123456\0Aauipc a0, 1\0Amv a0, a1\0Alw a4, $0\0Alb a5, -4(a7)\0A", "*m,~{x5},~{x9},~{x10},~{x14},~{x15}"(ptr elementtype(i32) %x) -------------------------------------------------------------------------------- /test/test_suite/asm/asm_load_rv64.c3t: -------------------------------------------------------------------------------- 1 | // #target: elf-riscv64 2 | module test; 3 | 4 | fn void main(String[] args) 5 | { 6 | int x = 2; 7 | asm 8 | { 9 | li $s1, -9223372036854775808; 10 | } 11 | } 12 | 13 | /* #expect: test.ll 14 | 15 | "li s1, -9223372036854775808\0A", "~{x9}"() -------------------------------------------------------------------------------- /test/test_suite/asm/asm_math_rv.c3t: -------------------------------------------------------------------------------- 1 | // #target: elf-riscv32 2 | module test; 3 | 4 | fn void main(String[] args) 5 | { 6 | int x = 0; 7 | asm 8 | { 9 | add $t0, $t1, $t2; 10 | add x, $t1, $t2; 11 | sub $a0, $a1, $a2; 12 | addi $s1, $s2, -2048; 13 | neg $t3, $t4; 14 | } 15 | } 16 | 17 | /* #expect: test.ll 18 | 19 | "add t0, t1, t2\0Aadd $0, t1, t2\0Asub a0, a1, a2\0Aaddi s1, s2, -2048\0Aneg t3, t4\0A", "=r,~{x5},~{x9},~{x10},~{x28}"() -------------------------------------------------------------------------------- /test/test_suite/asm/asm_set_rv.c3t: -------------------------------------------------------------------------------- 1 | // #target: elf-riscv32 2 | module test; 3 | 4 | fn void main(String[] args) 5 | { 6 | int x = 2; 7 | asm 8 | { 9 | slt $t0, $t1, x; 10 | slti $a0, $a1, -2048; 11 | sltiu $a0, $a1, 4095u; 12 | seqz $s0, $zero; 13 | } 14 | } 15 | 16 | /* #expect: test.ll 17 | 18 | "slt t0, t1, $0\0Aslti a0, a1, -2048\0Asltiu a0, a1, 4095\0Aseqz s0, zero\0A", "r,~{x5},~{x8},~{x10}"(i32 %1) -------------------------------------------------------------------------------- /test/test_suite/asm/asm_shift_rv.c3t: -------------------------------------------------------------------------------- 1 | // #target: elf-riscv32 2 | module test; 3 | 4 | fn void main(String[] args) 5 | { 6 | asm 7 | { 8 | sll $t0, $t1, $t2; 9 | slli $s1, $s2, 31u; 10 | srl $a0, $a1, $a2; 11 | srli $x10, $x11, 0u; 12 | sra $t0, $t1, $t2; 13 | srai $s1, $s2, 1u; 14 | } 15 | } 16 | 17 | /* #expect: test.ll 18 | 19 | "sll t0, t1, t2\0Aslli s1, s2, 31\0Asrl a0, a1, a2\0Asrli x10, x11, 0\0Asra t0, t1, t2\0Asrai s1, s2, 1\0A", "~{x5},~{x9},~{x10}"() -------------------------------------------------------------------------------- /test/test_suite/asm/asm_store_rv.c3t: -------------------------------------------------------------------------------- 1 | // #target: elf-riscv32 2 | module test; 3 | 4 | fn void main(String[] args) 5 | { 6 | int x = 2; 7 | int y = 0; 8 | asm 9 | { 10 | lw $a4, [&x]; 11 | sw $a4, [&y]; 12 | } 13 | } 14 | 15 | /* #expect: test.ll 16 | 17 | "lw a4, $1\0Asw a4, $0\0A", "=*m,*m,~{x14}"(ptr elementtype(i32) %y, ptr elementtype(i32) %x) -------------------------------------------------------------------------------- /test/test_suite/asm/naked.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module testing; 3 | 4 | fn void start() @export("_start") @naked @nostrip { 5 | asm { 6 | movq $rax, 0x3c; 7 | movq $rdi, 42; 8 | syscall; 9 | } 10 | } 11 | 12 | /* #expect: testing.ll 13 | 14 | define void @_start() #0 { 15 | entry: 16 | call void asm sideeffect alignstack "movq $$60, %rax\0Amovq $$42, %rdi\0Asyscall \0A", "~{cc},~{rax},~{rcx},~{r8},~{r11},~{flags},~{dirflag},~{fspr}"() 17 | ret void 18 | } 19 | 20 | -------------------------------------------------------------------------------- /test/test_suite/asm/syscall.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module testing; 3 | 4 | fn void start() @export("_start") @naked @nostrip { 5 | asm { 6 | syscall; 7 | } 8 | } 9 | 10 | /* #expect: testing.ll 11 | 12 | define void @_start() #0 { 13 | entry: 14 | call void asm sideeffect alignstack "syscall \0A", "~{cc},~{rax},~{rcx},~{r11},~{flags},~{dirflag},~{fspr}"() 15 | ret void 16 | } 17 | 18 | -------------------------------------------------------------------------------- /test/test_suite/assert/global_static_assert_not_constant.c3: -------------------------------------------------------------------------------- 1 | int x = 3; 2 | 3 | $assert x == 3; // #error: Compile time evaluation requires a compile time constant value. -------------------------------------------------------------------------------- /test/test_suite/assert/static_assert.c3: -------------------------------------------------------------------------------- 1 | 2 | const int FOO = 2; 3 | 4 | fn void test() 5 | { 6 | $assert FOO == 2 : "Bad"; 7 | $assert FOO == 0 : "Good"; // #error: Good 8 | } -------------------------------------------------------------------------------- /test/test_suite/attributes/attr_not_imported.c3: -------------------------------------------------------------------------------- 1 | module abc; 2 | 3 | def @Foo = { @inline }; 4 | 5 | module bar; 6 | 7 | fn void test() abc::@Foo {} // #error: Did you mean the attribute 8 | -------------------------------------------------------------------------------- /test/test_suite/attributes/attribute_params.c3: -------------------------------------------------------------------------------- 1 | def @Foo() = { @inline }; // #error: At least one parameter was expected 2 | def @Bar = { @inline }; 3 | 4 | fn void test1() @Foo { } 5 | fn void test2() @Foo() { } // #error: An expression was 6 | fn void test3() @Bar { } 7 | fn void test4() @Bar() { } // #error: An expression was -------------------------------------------------------------------------------- /test/test_suite/attributes/attribute_path.c3: -------------------------------------------------------------------------------- 1 | fn void test() abc::@inline // #error: Only user-defined attribute names 2 | { 3 | 4 | } -------------------------------------------------------------------------------- /test/test_suite/attributes/attribute_visibility.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | const int FOO @private = 4; 4 | def @Align(x) = { @align(x * FOO) }; 5 | 6 | module test2; 7 | import test; 8 | int black @Align(16) = 123; 9 | 10 | /* #expect: test2.ll 11 | 12 | @test2.black = local_unnamed_addr global i32 123, align 64 -------------------------------------------------------------------------------- /test/test_suite/attributes/attributes_repeat_param.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-aarch64 2 | module test; 3 | 4 | def @Test(x) = { @extern("Foo" +++ x) }; 5 | 6 | fn void hello_world() @Test("Megaman") 7 | {} 8 | 9 | fn void ello_world() @Test("Pegasus") 10 | {} 11 | 12 | fn int main() 13 | { 14 | hello_world(); 15 | ello_world(); 16 | return 0; 17 | } 18 | 19 | /* #expect: test.ll 20 | 21 | define i32 @main() #0 { 22 | entry: 23 | call void @FooMegaman() 24 | call void @FooPegasus() 25 | ret i32 0 26 | } 27 | -------------------------------------------------------------------------------- /test/test_suite/attributes/call_attribute_error_eos.c3: -------------------------------------------------------------------------------- 1 | fn void main() 2 | { 3 | call() // #error: ';' 4 | rl::bar(); 5 | } -------------------------------------------------------------------------------- /test/test_suite/attributes/recursive_attributes.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | def @Align(y) = { @Align16(y / 2) }; 4 | def @Align16(x) = { @align(4) @Align(8 * x) }; // #error: Recursive declaration of attribute 5 | def @Test = { @noinline }; 6 | struct Foo 7 | { 8 | int z; 9 | int xy @Align16(8); 10 | } 11 | 12 | Foo f; 13 | 14 | fn void testme() @Test 15 | { 16 | int x; 17 | } 18 | -------------------------------------------------------------------------------- /test/test_suite/attributes/wasm_import.c3t: -------------------------------------------------------------------------------- 1 | // #target: wasm32 2 | module test; 3 | extern fn void test() @wasm("hello", "world"); 4 | 5 | /* #expect: test.ll 6 | 7 | declare void @world() #0 8 | attributes #0 = { nounwind uwtable "no-trapping-math"="true" "stack-protector-buffer-size"="8" "wasm-export-name"="world" "wasm-import-module"="hello" "wasm-import-name"="world" } -------------------------------------------------------------------------------- /test/test_suite/attributes/wasm_module.c3: -------------------------------------------------------------------------------- 1 | 2 | fn void test() @wasm("hello", "world") { } // #error: Specifying a wasm import module 3 | extern fn void test2() @wasm("a", "b", "c"); // #error: Too many arguments to 4 | extern fn void test3() @extern("hello") @wasm("a"); // #error: An external name 5 | extern fn void test4() @extern("hello") @wasm("a", "b"); // #error: An external name -------------------------------------------------------------------------------- /test/test_suite/bitstruct/address_of_bitstruct.c3: -------------------------------------------------------------------------------- 1 | bitstruct BitField : char 2 | { 3 | int a : 0..2; 4 | int b : 4..5; 5 | int c : 6..7; 6 | } 7 | 8 | fn void test() 9 | { 10 | BitField x; 11 | BitField* z = &x; 12 | x.a; 13 | z.a; 14 | &x.a; // #error: You cannot take the address of a bitstruct member 15 | } -------------------------------------------------------------------------------- /test/test_suite/bitstruct/bistruct_cast_wrong_size.c3: -------------------------------------------------------------------------------- 1 | module bug_repro; 2 | 3 | bitstruct Edge_Flags : char { 4 | bool left; 5 | bool top; 6 | bool right; 7 | bool bottom; 8 | } 9 | 10 | fn int main() { 11 | Edge_Flags edges; 12 | Edge_Flags a = edges & (Edge_Flags)(1 << 0); // #error: 'int' 13 | return 0; 14 | } -------------------------------------------------------------------------------- /test/test_suite/bitstruct/bitstruct_cast_and_back.c3: -------------------------------------------------------------------------------- 1 | // See issue #1159 2 | 3 | bitstruct Foo : int { 4 | bool a; 5 | } 6 | 7 | bitstruct Bar : int { 8 | bool a; 9 | bool b; 10 | } 11 | 12 | fn void bitstruct_cast() { 13 | Bar bar; 14 | Foo foo = (Foo)(int)bar; 15 | } 16 | -------------------------------------------------------------------------------- /test/test_suite/bitstruct/bitstruct_cast_const_init.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | bitstruct Foo : int 4 | { 5 | int abc : 0..4; 6 | int defg : 23..26; 7 | } 8 | 9 | fn void main() 10 | { 11 | Foo f; 12 | int z = (int) Foo { .abc = 2, .defg = 1 }; 13 | } 14 | 15 | /* #expect: test.ll 16 | 17 | %f = alloca i32, align 4 18 | %z = alloca i32, align 4 19 | store i32 0, ptr %f, align 4 20 | store i32 8388610, ptr %z, align 4 -------------------------------------------------------------------------------- /test/test_suite/bitstruct/bitstruct_init_bool.c3t: -------------------------------------------------------------------------------- 1 | module foo; 2 | 3 | bitstruct Foo : int 4 | { 5 | bool a : 1; 6 | bool b : 2; 7 | bool c : 3; 8 | } 9 | 10 | fn void test() 11 | { 12 | Foo f = { .a = true, .b = false }; 13 | } 14 | 15 | /* #expect: foo.ll 16 | 17 | define void @foo.test() #0 { 18 | entry: 19 | %f = alloca i32, align 4 20 | store i32 2, ptr %f, align 4 21 | ret void 22 | } -------------------------------------------------------------------------------- /test/test_suite/bitstruct/bitstruct_simple.c3: -------------------------------------------------------------------------------- 1 | bitstruct Foo : char 2 | { 3 | bool a; 4 | int b; // #error: For bitstructs without bit ranges, the types must all be 'bool' 5 | } 6 | 7 | bitstruct Foo2 : char 8 | { 9 | bool a0; 10 | bool a1; 11 | bool a2; 12 | bool a3; 13 | bool a4; 14 | bool a5; 15 | bool a6; 16 | bool a7; 17 | bool a8; // #error: overflow 18 | } -------------------------------------------------------------------------------- /test/test_suite/bitstruct/bitstruct_simple_err_decl.c3: -------------------------------------------------------------------------------- 1 | bitstruct Foo : char 2 | { 3 | bool a : 1; 4 | bool b; // #error: remove ranges from the other member 5 | } 6 | 7 | bitstruct Foo2 : char 8 | { 9 | bool a; 10 | bool b : 1; // #error: ranges to all other members 11 | } -------------------------------------------------------------------------------- /test/test_suite/bitstruct/bitstruct_single_error.c3: -------------------------------------------------------------------------------- 1 | bitstruct Foo1 : char 2 | { 3 | char x : 1..1; 4 | } 5 | 6 | bitstruct Foo2 : char 7 | { 8 | char x : 1; // #error: Only booleans may use non-range indices 9 | } 10 | 11 | bitstruct Foo3 : char 12 | { 13 | bool x : 0..2; // #error: The bit width of 'bool' 14 | } 15 | 16 | bitstruct Foo4 : int 17 | { 18 | char x : 0..15; // #error: The bit width of 'char' 19 | } -------------------------------------------------------------------------------- /test/test_suite/bitstruct/invalid_bitstruct_type.c3: -------------------------------------------------------------------------------- 1 | 2 | bitstruct Test : float // #error: The type of the bitstruct cannot be 'float' but must be an integer or an array of integers. 3 | { 4 | int a : 1..3; 5 | int b : 5..10; 6 | uint c : 20..20; 7 | } -------------------------------------------------------------------------------- /test/test_suite/bitstruct/invalid_empty_struct_union.c3: -------------------------------------------------------------------------------- 1 | struct Foo // #error: Zero sized structs are not permitted. 2 | { 3 | } 4 | 5 | union Bar // #error: Zero sized unions are not permitted. 6 | { 7 | } -------------------------------------------------------------------------------- /test/test_suite/bitstruct/missing_bitstruct_type.c3: -------------------------------------------------------------------------------- 1 | bitstruct BitField 2 | { // #error: followed by bitstruct 3 | } -------------------------------------------------------------------------------- /test/test_suite/bitstruct/param_bitstruct.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module foo; 3 | 4 | bitstruct Abc : uint 5 | { 6 | bool x : 0; 7 | } 8 | 9 | fn void test(Abc x) 10 | { 11 | x.x = false; 12 | } 13 | 14 | /* #expect: foo.ll 15 | 16 | define void @foo.test(i32 %0) #0 { 17 | entry: 18 | %x = alloca i32, align 4 19 | store i32 %0, ptr %x, align 4 20 | %1 = load i32, ptr %x, align 4 21 | %2 = and i32 %1, -2 22 | store i32 %2, ptr %x, align 4 23 | ret void 24 | } -------------------------------------------------------------------------------- /test/test_suite/builtins/builtin_vector_abs.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | fn void main() 4 | { 5 | { 6 | float[<2>] vf1 = { 1, -1 }; 7 | float[<2>] absf = $$abs(vf1); 8 | } 9 | { 10 | int[<2>] v1 = { 1, -1 }; 11 | int[<2>] absi = $$abs(v1); 12 | } 13 | } 14 | 15 | /* #expect: test.ll 16 | 17 | %1 = call <2 x float> @llvm.fabs.v2f32(<2 x float> %0) 18 | %3 = call <2 x i32> @llvm.abs.v2i32(<2 x i32> %2, i1 false) 19 | -------------------------------------------------------------------------------- /test/test_suite/builtins/builtin_with_optional.c3: -------------------------------------------------------------------------------- 1 | fn void main() 2 | { 3 | float x; 4 | x = $$fma(x, x, x); 5 | float! y; 6 | y = $$fma(x, x, y); 7 | x = $$fma(x, x, y); // #error: 'float!' 8 | } -------------------------------------------------------------------------------- /test/test_suite/builtins/prefetch.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | import std::io; 4 | 5 | fn void main() 6 | { 7 | int a; 8 | $$prefetch(&a, 1, 3); 9 | $$prefetch(&a, 0, 1); 10 | @prefetch(&a); 11 | } 12 | 13 | /* #expect: test.ll 14 | 15 | %a = alloca i32, align 4 16 | store i32 0, ptr %a, align 4 17 | call void @llvm.prefetch.p0(ptr %a, i32 1, i32 3, i32 1) 18 | call void @llvm.prefetch.p0(ptr %a, i32 0, i32 1, i32 1) 19 | call void @llvm.prefetch.p0(ptr %a, i32 0, i32 3, i32 1) 20 | -------------------------------------------------------------------------------- /test/test_suite/builtins/reverse_builtin.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | 3 | module test; 4 | import std::io; 5 | 6 | fn void main() 7 | { 8 | int[<4>] a = { 1, -3, 5, -7 }; 9 | io::printfn("%s", $$reverse(a)); 10 | } 11 | 12 | /* #expect: test.ll 13 | 14 | %reverse = shufflevector <4 x i32> %0, <4 x i32> poison, <4 x i32> -------------------------------------------------------------------------------- /test/test_suite/builtins/trap.c3t: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | fn void main() 4 | { 5 | $$breakpoint(); 6 | $$trap(); 7 | } 8 | 9 | /* #expect: test.ll 10 | 11 | call void @llvm.debugtrap() 12 | call void @llvm.trap() 13 | -------------------------------------------------------------------------------- /test/test_suite/cast/cast_ok.c3: -------------------------------------------------------------------------------- 1 | struct Foo { int a; } 2 | 3 | fn void test4() 4 | { 5 | int x = (int)(32); 6 | } 7 | 8 | fn void test5() 9 | { 10 | Foo x = (Foo)(Foo{32}); 11 | } -------------------------------------------------------------------------------- /test/test_suite/cast/cast_parse_fails.c3: -------------------------------------------------------------------------------- 1 | struct Foo { int a; } 2 | 3 | fn void test2() 4 | { 5 | int x = int{ 32 }; // #error: 'int' cannot use compound literal initialization, did you intend to use a cast 6 | } 7 | 8 | fn void test3() 9 | { 10 | int x = int(32); // #error: A type cannot be followed by (), if you intended a cast, use '(type) expression' 11 | } 12 | 13 | 14 | -------------------------------------------------------------------------------- /test/test_suite/cast/cast_parse_fails2.c3: -------------------------------------------------------------------------------- 1 | 2 | struct Foo { int a; } 3 | 4 | fn void test1() 5 | { 6 | (Foo)({ 32 }); 7 | Foo({ 32 }); // #error: A type cannot be followed by (), if you intended a cast, use '(type) expression' 8 | } -------------------------------------------------------------------------------- /test/test_suite/cast/cast_slice_implicit.c3: -------------------------------------------------------------------------------- 1 | fn void foo() 2 | { 3 | int[] array; 4 | int* ptr = array; 5 | void* ptr2 = &array; 6 | int* ptr3 = &array; // #error: is not permitted 7 | } -------------------------------------------------------------------------------- /test/test_suite/cast/cast_string_to_infered_array.c3: -------------------------------------------------------------------------------- 1 | import std; 2 | fn void main() 3 | { 4 | char[?]* x = "abc"; // #error: You cannot cast 'String' to 'char[?]*' 5 | io::printn($typeof(x).nameof); 6 | } -------------------------------------------------------------------------------- /test/test_suite/cast/cast_struct_fails.c3: -------------------------------------------------------------------------------- 1 | struct Foo 2 | { 3 | int a; 4 | float b; 5 | } 6 | 7 | struct Bar 8 | { 9 | int b; 10 | float c; 11 | } 12 | 13 | struct Baz 14 | { 15 | int b; 16 | int c; 17 | } 18 | 19 | struct BazTwo 20 | { 21 | int[2] d; 22 | int e; 23 | } 24 | 25 | fn void test1() 26 | { 27 | Foo x; 28 | Bar z = (Baz)(x); // #error: 'Foo' to 'Baz' 29 | } 30 | fn void test2() 31 | { 32 | Baz x; 33 | BazTwo z = (BazTwo)(x); // #error: 'Baz' to 'BazTwo' 34 | } 35 | 36 | -------------------------------------------------------------------------------- /test/test_suite/cast/cast_to_failable.c3: -------------------------------------------------------------------------------- 1 | fault MyErr 2 | { 3 | FOO 4 | } 5 | 6 | fn void test() 7 | { 8 | int! x; 9 | double! y; 10 | int! d = ($typeof(MyErr.FOO?))(x); // #error: Casting to an optional 11 | int! df = ($typeof(y))(x); // #error: Casting to an optional type is not allowed 12 | double! df2 = ($typeof(y!!))(x); 13 | } 14 | 15 | -------------------------------------------------------------------------------- /test/test_suite/cast/cast_untyped_list_error.c3: -------------------------------------------------------------------------------- 1 | module testing; 2 | 3 | fn void main() 4 | { 5 | (void){}; // #error: You cannot cast 'untyped_list' to 'void' 6 | } -------------------------------------------------------------------------------- /test/test_suite/cast/implicit_array_ptr_conv.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | fn void test(int[5]* x) {} 4 | fn void test2(int* x) {} 5 | 6 | fn int main() 7 | { 8 | int[5][5] y; 9 | test(&y); 10 | test2(&y); 11 | return 0; 12 | } -------------------------------------------------------------------------------- /test/test_suite/cast/implicit_void_ptr_deep.c3: -------------------------------------------------------------------------------- 1 | fn void main() 2 | { 3 | int** y; 4 | int* z; 5 | void** x = y; 6 | void** z2 = z; // #error: Implicitly casting 7 | } -------------------------------------------------------------------------------- /test/test_suite/cast/inner_type_cast.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | struct Foo 4 | { 5 | bitstruct abc : int 6 | { 7 | bool a; 8 | } 9 | } 10 | 11 | fn void test1() 12 | { 13 | Foo x; 14 | x.abc = "abc"; // #error: to the inner type 'Foo.abc' 15 | } 16 | 17 | fn void test2() 18 | { 19 | Foo x; 20 | x.abc = 2; // #error: type 'Foo.abc' is not permitted, but you may do an explicit 21 | } -------------------------------------------------------------------------------- /test/test_suite/comments/simple_comments.c3: -------------------------------------------------------------------------------- 1 | module comments; 2 | /* Span *//* style */ 3 | 4 | /* Nested /* Errors // Inside */ */ 5 | // Single line 6 | /* 7 | Multiline span style 8 | */ 9 | 10 | fn void test() 11 | { 12 | return; 13 | } 14 | 15 | /* /* nested /* comments! */ !! */ goes here */ 16 | -------------------------------------------------------------------------------- /test/test_suite/compile_time/add_to_ct_undefined.c3: -------------------------------------------------------------------------------- 1 | fn int main() 2 | { 3 | var $a; 4 | $a += 1; // #error: not yet initialized 5 | return 0; 6 | } -------------------------------------------------------------------------------- /test/test_suite/compile_time/concat_const.c3: -------------------------------------------------------------------------------- 1 | module wi3enrich; 2 | import std::io; 3 | import std::os::env; 4 | 5 | macro String to_string(uint $num) @const 6 | { 7 | char[] $res; 8 | int $i = 0; 9 | $for (;$num != 0;) 10 | $res = $res +++ (char) ('0' + $num % 10); 11 | $num = $num / 10; 12 | $i++; 13 | $endfor 14 | $res = $res +++ '\0'; 15 | return (String) $res; 16 | } 17 | 18 | fn int main(String[] args) 19 | { 20 | io::printn(to_string(4)); 21 | return 0; 22 | } 23 | -------------------------------------------------------------------------------- /test/test_suite/compile_time/concat_slice_bytes.c3t: -------------------------------------------------------------------------------- 1 | module test; 2 | import std; 3 | 4 | fn void main() 5 | { 6 | String $a = "hello"; 7 | char[] $b = { 'a', 'b' }; 8 | var $c = $a +++ $b; 9 | String y = $c; 10 | char[3] $bytes = x'0103ff'; 11 | var $d = $bytes +++ $b; 12 | char[5] z = $d; 13 | } 14 | 15 | /* #expect: test.ll 16 | 17 | @.str = private unnamed_addr constant [8 x i8] c"helloab\00", align 1 18 | @.bytes = private unnamed_addr constant [6 x i8] c"\01\03\FFab\00", align 1 -------------------------------------------------------------------------------- /test/test_suite/compile_time/concat_zero_slice.c3t: -------------------------------------------------------------------------------- 1 | fn int main() 2 | { 3 | char[] $res; 4 | $res = { '0' } +++ $res; 5 | return 0; 6 | } -------------------------------------------------------------------------------- /test/test_suite/compile_time/ct_and_or.c3: -------------------------------------------------------------------------------- 1 | fn void test() 2 | { 3 | $assert false ||| false ||| true ||| hello(""); 4 | $assert !(false &&& hello("")); 5 | $assert !(true &&& true &&& false &&& hello("")); 6 | } -------------------------------------------------------------------------------- /test/test_suite/compile_time/ct_cast_example.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | import std; 4 | 5 | fn void main() 6 | { 7 | var $x = { 1, 2 }; 8 | $x = $x +++ 333; 9 | io::printn((int[?])$x); 10 | } 11 | 12 | /* #expect: test.ll 13 | 14 | @.__const = private unnamed_addr constant [3 x i32] [i32 1, i32 2, i32 333], align 4 15 | -------------------------------------------------------------------------------- /test/test_suite/compile_time/ct_else_else.c3: -------------------------------------------------------------------------------- 1 | // Issue #1824 2 | fn void main() 3 | { 4 | $if true: 5 | $else 6 | $else // #error: Expected '$endif' 7 | $endif 8 | } -------------------------------------------------------------------------------- /test/test_suite/compile_time/ct_eval_sym.c3: -------------------------------------------------------------------------------- 1 | fn int test() 2 | { 3 | void* x = (void*)&$eval($$FUNC); 4 | return 1; 5 | } -------------------------------------------------------------------------------- /test/test_suite/compile_time/ct_eval_wrong.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | fn void main() 4 | { 5 | $eval("foo()"); // #error: with $eval 6 | } 7 | fn void foo() 8 | { 9 | io::printfn("foo"); 10 | } -------------------------------------------------------------------------------- /test/test_suite/compile_time/ct_if.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | int x @if(false) = 1; 3 | 4 | int d @if(true) = 5; 5 | 6 | /* #expect: ct_if.ll 7 | 8 | @ct_if.d = local_unnamed_addr global i32 5, align 4 9 | -------------------------------------------------------------------------------- /test/test_suite/compile_time/ct_left_hand_assign.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module foo; 3 | import std; 4 | 5 | macro @foo(#arg) 6 | { 7 | #arg++; 8 | } 9 | 10 | module bar; 11 | import foo; 12 | 13 | fn void main() 14 | { 15 | int $c = 0; 16 | foo::@foo($c); 17 | } 18 | 19 | /* #expect: bar.ll 20 | 21 | entry: 22 | ret void 23 | } -------------------------------------------------------------------------------- /test/test_suite/compile_time/ct_ordered_error.c3t: -------------------------------------------------------------------------------- 1 | module test; 2 | const ABC = 1; 3 | const A @if(ABC == 1) = 100 ; 4 | int b @if(A == 100); // #error: This @if expression is dependent on -------------------------------------------------------------------------------- /test/test_suite/compile_time/ct_string_functions.c3t: -------------------------------------------------------------------------------- 1 | import std; 2 | 3 | fn int main() 4 | { 5 | $assert(@str_upper("Hello World") == "HELLO WORLD"); 6 | $assert(@str_lower("Hello World") == "hello world"); 7 | $assert(@str_find("Hello World", "o") == 4); 8 | $assert(@str_find("Hello World", "w") == -1); 9 | $assert(@str_hash("Hello C3") == 487972447); 10 | return 0; 11 | } -------------------------------------------------------------------------------- /test/test_suite/compile_time/ct_vaexpr_assign.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | import std; 4 | macro foo(...) 5 | { 6 | $vaexpr[0] = 2; 7 | } 8 | 9 | fn void main() 10 | { 11 | int $x; 12 | foo($x); 13 | int y = $x; 14 | } 15 | 16 | /* #expect: test.ll 17 | 18 | define void @test.main() #0 { 19 | entry: 20 | %y = alloca i32, align 4 21 | store i32 2, ptr %y, align 4 22 | ret void 23 | } 24 | -------------------------------------------------------------------------------- /test/test_suite/compile_time/cttype_reassign.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module reassign; 3 | 4 | fn void test() 5 | { 6 | var $Foo = double; 7 | $Foo = int; 8 | $Foo hello; 9 | } 10 | 11 | /* #expect: reassign.ll 12 | 13 | %hello = alloca i32, align 4 14 | store i32 0, ptr %hello, align 4 15 | ret void -------------------------------------------------------------------------------- /test/test_suite/compile_time/deep_stringify.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | macro @foo(#foo) => @bar(#foo); 4 | macro @bar(#bar) 5 | { 6 | return "#bar contains " +++ $stringify(#bar); 7 | } 8 | 9 | fn void main() 10 | { 11 | String a = @foo(something); 12 | } 13 | 14 | /* #expect: test.ll 15 | 16 | @.str = private unnamed_addr constant [24 x i8] c"#bar contains something\00", align 1 17 | 18 | entry: 19 | %a = alloca %"char[]", align 8 20 | store %"char[]" { ptr @.str, i64 23 }, ptr %a, align 8 21 | ret void 22 | } 23 | -------------------------------------------------------------------------------- /test/test_suite/compile_time/mod_ct.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | fn int main() 4 | { 5 | double a = 4.5 % 5; 6 | double b = -4.5 % 5; 7 | int ai = 4 % 5; 8 | int bi = -4 % 5; 9 | return 0; 10 | } 11 | 12 | /* #expect: test.ll 13 | 14 | store double 4.500000e+00, ptr %a, align 8 15 | store double -4.500000e+00, ptr %b, align 8 16 | store i32 4, ptr %ai, align 4 17 | store i32 -4, ptr %bi, align 4 -------------------------------------------------------------------------------- /test/test_suite/compile_time/not_cost.c3: -------------------------------------------------------------------------------- 1 | macro foo($a) @const 2 | { 3 | int a = $a; 4 | return $a; 5 | } 6 | 7 | fn void test() 8 | { 9 | foo(123); // #error: failed to fold to a constant value 10 | } -------------------------------------------------------------------------------- /test/test_suite/compile_time/not_yet_initialized.c3: -------------------------------------------------------------------------------- 1 | macro foo($Foo) 2 | { 3 | $Foo a; 4 | return a; 5 | } 6 | 7 | fn void test1() 8 | { 9 | var $Bar; 10 | foo($Bar); // #error: You need to assign a type to 11 | } 12 | 13 | fn void test2() 14 | { 15 | var $Bar; 16 | $Bar z; // #error: You need to assign a type to 17 | } 18 | -------------------------------------------------------------------------------- /test/test_suite/compile_time/stringify2.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | import std::io; 4 | 5 | fn void main() 6 | { 7 | var $s1 = $stringify(1 + 2); 8 | char[?] s2 = $stringify($s1); 9 | char[] s3 = $s1; 10 | 11 | io::printfn("$s1 == %s", $s1); 12 | io::printfn("s2 == %s", &s2); 13 | io::printfn("s3 == %s", s3); 14 | } 15 | 16 | /* #expect: test.ll 17 | 18 | c"$s1\00", align 1 19 | c"1 + 2\00", align 1 20 | c"1 + 2\00", align 1 -------------------------------------------------------------------------------- /test/test_suite/compile_time/typefrom.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | 3 | module test; 4 | 5 | 6 | fn int main() 7 | { 8 | var $foo = double.typeid; 9 | $typefrom($foo) a = 123.0; 10 | return (int)a; 11 | } 12 | 13 | /* #expect: test.ll 14 | 15 | %a = alloca double, align 8 -------------------------------------------------------------------------------- /test/test_suite/compile_time/typefrom_errors.c3t: -------------------------------------------------------------------------------- 1 | 2 | fn void test() 3 | { 4 | typeid x; 5 | $typefrom(2 > 1 ? int.typeid : double.typeid) xf; 6 | $typefrom(x) a; // #error: Expected a constant 7 | } 8 | 9 | fn void test2() 10 | { 11 | var $x = 1; 12 | $typefrom($x) a; // #error: Expected a constant 13 | } -------------------------------------------------------------------------------- /test/test_suite/compile_time/typeof_from_literal.c3: -------------------------------------------------------------------------------- 1 | module foo; 2 | 3 | fn void a() 4 | { 5 | $typeof(9146744073709551615i64) ef; 6 | int fffx = ef; // #error: 'long' 7 | } 8 | 9 | fn void b() 10 | { 11 | $typeof(9223372036854775809u64) ef; 12 | int fffx = ef; // #error: 'ulong' 13 | } 14 | 15 | -------------------------------------------------------------------------------- /test/test_suite/compile_time/untyped_with_inferred.c3: -------------------------------------------------------------------------------- 1 | 2 | fn void main() 3 | { 4 | var $x = { 1, 1.0 }; 5 | double[?] z = $x; 6 | } 7 | -------------------------------------------------------------------------------- /test/test_suite/compile_time_introspection/defined2.c3: -------------------------------------------------------------------------------- 1 | fn void main() 2 | { 3 | int[<2>] ab = { 11, 22 }; 4 | $assert !$defined(&1); 5 | int! a; 6 | $assert $defined(a!!); 7 | $assert !$defined(ab!!); 8 | $assert $defined(a!); 9 | $assert !$defined(ab!); 10 | $assert !$defined(*ab); 11 | int* z = &&1; 12 | $assert $defined(*z); 13 | void* g; 14 | $assert !$defined(*g); 15 | } -------------------------------------------------------------------------------- /test/test_suite/compile_time_introspection/defined_builtin.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module foo; 3 | fn void test() 4 | { 5 | bool a = $defined($$sin); 6 | bool b = $defined($$bas); 7 | } 8 | 9 | /* #expect: foo.ll 10 | 11 | define void @foo.test() #0 { 12 | entry: 13 | %a = alloca i8, align 1 14 | %b = alloca i8, align 1 15 | store i8 1, ptr %a, align 1 16 | store i8 0, ptr %b, align 1 17 | ret void 18 | } -------------------------------------------------------------------------------- /test/test_suite/compile_time_introspection/defined_subscript.c3: -------------------------------------------------------------------------------- 1 | fn void main() 2 | { 3 | int[<2>] ab = { 11, 22 }; 4 | $assert !$defined(ab[3]); 5 | $assert $defined(ab[1]); 6 | $assert !$defined(ab[0][0]); 7 | } -------------------------------------------------------------------------------- /test/test_suite/compile_time_introspection/recursive_tag.c3: -------------------------------------------------------------------------------- 1 | enum Test @tag("test", Test.FOO) {FOO} // #error: Recursive definition of 'Test' 2 | 3 | def @Test(Foo val) = {}; 4 | 5 | enum Foo @tag("test", Foo.BAR) // #error: Recursive definition of 'Foo' 6 | { 7 | BAR, 8 | BAZ 9 | } 10 | 11 | fn void main() @Test(BAR) 12 | { 13 | } 14 | -------------------------------------------------------------------------------- /test/test_suite/constants/assign_to_const.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::io; 3 | 4 | fn void main() 5 | { 6 | const NUM = 4; 7 | NUM += 1; // #error: You cannot assign to a constant 8 | } -------------------------------------------------------------------------------- /test/test_suite/constants/byte_literal_fail_base64.c3: -------------------------------------------------------------------------------- 1 | char[?] foo64 = b64"SGVsbG8g!V29ybGQ="; // #error: '!' is not a valid base64 character -------------------------------------------------------------------------------- /test/test_suite/constants/byte_literal_fail_base64_2.c3: -------------------------------------------------------------------------------- 1 | char[?] foo64 = b64"SGVsbG8gV29y=bGQ="; // #error: 'b' can't be placed after an ending '=' -------------------------------------------------------------------------------- /test/test_suite/constants/byte_literal_fail_base64_4.c3: -------------------------------------------------------------------------------- 1 | char[?] foo64 = b64"SGVsbG8gV29ybGQ==="; // #error: There cannot be more than -------------------------------------------------------------------------------- /test/test_suite/constants/byte_literal_fail_hex.c3: -------------------------------------------------------------------------------- 1 | char[?] foo64 = x"abc def ^"; // #error: '^' isn't a valid hexadecimal digit, all digits should be a-z, A-Z and 0-9. 2 | -------------------------------------------------------------------------------- /test/test_suite/constants/constant_struct.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | struct Abc 4 | { 5 | int a; 6 | } 7 | 8 | struct Bcd 9 | { 10 | Abc x; 11 | } 12 | 13 | const Abc FOO = { 2 }; 14 | 15 | fn void main() 16 | { 17 | Bcd a = { FOO }; 18 | } 19 | -------------------------------------------------------------------------------- /test/test_suite/constants/empty_byte_literal.c3: -------------------------------------------------------------------------------- 1 | import std; 2 | 3 | fn void main() 4 | { 5 | char[] cd = {}; 6 | char[?] b = x""; // #error: must be at least 1 byte 7 | io::printfn("%d", b.len); 8 | } -------------------------------------------------------------------------------- /test/test_suite/constants/float_type.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | uint f0 = $typeof(1.0f).sizeof; 4 | uint f32 = $typeof(1.0f32).sizeof; 5 | uint f64 = $typeof(1.0f64).sizeof; 6 | 7 | /* #expect: test.ll 8 | 9 | @test.f0 = local_unnamed_addr global i32 4, align 4 10 | @test.f32 = local_unnamed_addr global i32 4, align 4 11 | @test.f64 = local_unnamed_addr global i32 8, align 4 -------------------------------------------------------------------------------- /test/test_suite/constants/init_order.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | 4 | macro foo() 5 | { 6 | $if $defined(A): 7 | return A + 1; 8 | $else 9 | return 1; 10 | $endif 11 | } 12 | 13 | const Z = foo(); 14 | 15 | const A @if(!$defined(A) && Z == 1) = 222; 16 | 17 | const B = foo(); 18 | 19 | /* #expect: test.ll 20 | 21 | @test.Z = local_unnamed_addr constant i32 1, align 4 22 | @test.B = local_unnamed_addr constant i32 223, align 4 23 | @test.A = local_unnamed_addr constant i32 222, align 4 -------------------------------------------------------------------------------- /test/test_suite/contracts/ct_eval_of_ensure.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | <* 3 | @ensure return > 100 4 | *> 5 | fn int test(int baz) 6 | { 7 | return 1; // #error: @ensure "return > 100" violated. 8 | } 9 | 10 | extern fn void printf(char*, ...); 11 | fn void main(String[] args) 12 | { 13 | test(1022); 14 | printf("Hello\n"); 15 | } 16 | 17 | -------------------------------------------------------------------------------- /test/test_suite/contracts/ensure_unsigned.c3: -------------------------------------------------------------------------------- 1 | 2 | // Check that 0 <= buf is ok. 3 | <* 4 | @ensure return <= buf.len 5 | *> 6 | fn usz foo(char[] buf) { 7 | if (buf.len == 0) return 0; 8 | // ... return some index into buf 9 | return buf.len; 10 | } -------------------------------------------------------------------------------- /test/test_suite/contracts/in_array.c3: -------------------------------------------------------------------------------- 1 | <* 2 | @param [in] x 3 | *> 4 | fn void test(int* x) 5 | { 6 | x[1] = 123; // #error: 'in' parameters may not be assigned to 7 | } 8 | fn int main() 9 | { 10 | test(&&int[3]{ 1, 2, 1 }); 11 | return 0; 12 | } -------------------------------------------------------------------------------- /test/test_suite/contracts/in_out.c3: -------------------------------------------------------------------------------- 1 | struct Foo { int x; } 2 | <* @param [out] f *> 3 | fn void bar(Foo* f) 4 | { 5 | f.x = 123; 6 | } 7 | 8 | <* @param [in] f *> 9 | fn void foo(Foo* f) 10 | { 11 | bar(f); // #error: macro as an 'out' argument 12 | } 13 | 14 | <* @param [in] f *> 15 | fn void foo2(Foo* f) 16 | { 17 | } 18 | 19 | <* @param [out] f *> 20 | fn void baz(Foo *f) 21 | { 22 | foo2(f); // #error: may not be passed into a function 23 | } -------------------------------------------------------------------------------- /test/test_suite/contracts/macro_ensure_static.c3: -------------------------------------------------------------------------------- 1 | module debugstuff; 2 | 3 | 4 | <* @ensure return > 0 *> 5 | macro check(int a) 6 | { 7 | if (a > 0) return 1; 8 | if (a < 0) return -1; // #error: @ensure 9 | return 100; 10 | } 11 | fn void main() 12 | { 13 | check(43); 14 | } -------------------------------------------------------------------------------- /test/test_suite/contracts/out_subscript.c3: -------------------------------------------------------------------------------- 1 | <* 2 | @param [out] z 3 | @param [out] out_data 4 | *> 5 | fn void tes2t(char* z, char[] out_data, char[] in_data) { 6 | z[0] = 2; 7 | z[0] += 1; // #error: 'out' parameters may not be read 8 | out_data[0] = 3; 9 | out_data[0] *= 1; // #error: 'out' parameters may not be read 10 | out_data[0..3]; // #error: 'out' parameters may not be read 11 | out_data[0..3] = 23; 12 | } -------------------------------------------------------------------------------- /test/test_suite/contracts/pure.c3: -------------------------------------------------------------------------------- 1 | module inlineme; 2 | 3 | <* 4 | @pure 5 | *> 6 | fn void test() 7 | { 8 | int x = 123; 9 | int* y = &x; 10 | } 11 | 12 | int abc; 13 | fn void test2() 14 | { 15 | abc = 1233; 16 | } 17 | 18 | <* @pure *> 19 | fn void test3() 20 | { 21 | abc = 1233; // #error: '@pure' functions may not access globals 22 | } -------------------------------------------------------------------------------- /test/test_suite/contracts/pure_calls.c3: -------------------------------------------------------------------------------- 1 | module inlineme; 2 | 3 | <* 4 | @pure 5 | *> 6 | fn void test() 7 | { 8 | int x = 123; 9 | int* y = &x; 10 | test3(); 11 | test2() @pure; 12 | test2(); // #error: Only '@pure' functions may be called, you can override this with an attribute 13 | } 14 | 15 | int abc; 16 | fn void test2() 17 | { 18 | abc = 1233; 19 | } 20 | 21 | <* @pure *> 22 | fn void test3() 23 | { 24 | } -------------------------------------------------------------------------------- /test/test_suite/contracts/require_contract_loc.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | fn void main() 3 | { 4 | int a; 5 | bitorder::read(a, int); // #error: violated 6 | } -------------------------------------------------------------------------------- /test/test_suite/defer/defer_try_catch.c3t: -------------------------------------------------------------------------------- 1 | // Check that this work. 2 | import std::net; 3 | 4 | fn void main() { 5 | Socket s; 6 | defer { 7 | char[1024] buf; 8 | while (try s.read(&buf)); 9 | } 10 | } -------------------------------------------------------------------------------- /test/test_suite/defer/defer_with_rethrow.c3: -------------------------------------------------------------------------------- 1 | fn int! foo() 2 | { return 1; } 3 | 4 | 5 | fn int! bar() 6 | { 7 | defer { 8 | {| 9 | foo()!; 10 | |}!!; 11 | } 12 | defer foo()!; // #error: Rethrows are not allowed inside of defers. 13 | return 1; 14 | } -------------------------------------------------------------------------------- /test/test_suite/defer/defer_with_return.c3: -------------------------------------------------------------------------------- 1 | fn int! bar() 2 | { 3 | defer { 4 | (void){| 5 | return 4; 6 | |}; 7 | } 8 | defer return 3; // #error: Return is not allowed inside of a defer 9 | return 1; 10 | } -------------------------------------------------------------------------------- /test/test_suite/define/alias_typename.c3: -------------------------------------------------------------------------------- 1 | def ShouldNotBeUppercase = FOO; // #error: A constant may not have a type name 2 | def ShouldNotBeUppercase2 = abc; // #error: An identifier may not be aliased -------------------------------------------------------------------------------- /test/test_suite/define/common2.c3: -------------------------------------------------------------------------------- 1 | int ofek; 2 | const OFKEOK = 2; 3 | distinct Helo = int; 4 | fn void Helo.test(&self) {} 5 | 6 | def hupp = Helo.test; 7 | def AOFKE = ofek; // #error: An uppercase alias is expected 8 | def okfoe = OFKEOK; // #error: An alias starting with a lower 9 | def helo = Helo; // #error: To alias a type 10 | def HELO = Helo; // #error: To alias a type 11 | -------------------------------------------------------------------------------- /test/test_suite/define/define_name_errors.c3: -------------------------------------------------------------------------------- 1 | 2 | def Foo = int; 3 | 4 | def hello1 = int; // #error: To alias a type, the alias 5 | def hello2 = Foo; // #error: To alias a type, the alias 6 | 7 | def HELLO1 = int; // #error: To alias a type, the alias 8 | def HELLO2 = Foo; // #error: To alias a type, the alias -------------------------------------------------------------------------------- /test/test_suite/define/forbidden_defines.c3: -------------------------------------------------------------------------------- 1 | def Abc = int[?]; // #error: Inferred array types can only 2 | def Bcd = anyfault; 3 | def Efd = any; 4 | -------------------------------------------------------------------------------- /test/test_suite/define/test_at_alias.c3: -------------------------------------------------------------------------------- 1 | module foo(); 2 | import std::io; 3 | 4 | macro @hello(Type thing) { 5 | io::printfn("%d", $sizeof(thing)); 6 | } 7 | 8 | module bar; 9 | 10 | import foo @public; 11 | 12 | def @intHello = foo::@hello(); 13 | 14 | fn void main(String[] args) { 15 | @intHello(42); 16 | } -------------------------------------------------------------------------------- /test/test_suite/distinct/disntinct_add_fail.c3: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | import std; 4 | 5 | fn void main() 6 | { 7 | DString y; 8 | 9 | y ^= 1; // #error: Expected an integer here 10 | y += 1.0; // #error: A value of type 'DString' 11 | y += 1; // #error: A value of type 'DString' 12 | } 13 | -------------------------------------------------------------------------------- /test/test_suite/distinct/distinct_add.c3: -------------------------------------------------------------------------------- 1 | import std; 2 | fn void main() 3 | { 4 | ZString a = "abc"; 5 | ZString b = a + 1; 6 | io::printfn("%s", b); 7 | } 8 | -------------------------------------------------------------------------------- /test/test_suite/distinct/distinct_function_call.c3: -------------------------------------------------------------------------------- 1 | def Abc = fn void(); 2 | distinct Foo = inline Abc; 3 | struct Bar 4 | { 5 | inline Abc a; 6 | } 7 | fn void test() 8 | { 9 | } 10 | fn void main() 11 | { 12 | Foo f = &test; 13 | Bar b = { &test }; 14 | f(); 15 | b(); // #error: may be invoked 16 | } -------------------------------------------------------------------------------- /test/test_suite/distinct/distinct_inline_access.c3: -------------------------------------------------------------------------------- 1 | module testing; 2 | import std::io; 3 | import foo; 4 | 5 | fn void main() 6 | { 7 | FooInt foo; 8 | } 9 | 10 | distinct FooInt = inline Foo; 11 | 12 | struct Bar 13 | { 14 | FooInt list; 15 | } 16 | 17 | fn void Bar.set(&self, int x) 18 | { 19 | self.list.set(x); 20 | } 21 | 22 | module foo; 23 | 24 | struct Foo 25 | { 26 | int x; 27 | } 28 | 29 | fn void Foo.set(&self, int x) 30 | { 31 | self.x = x; 32 | } -------------------------------------------------------------------------------- /test/test_suite/distinct/distinct_invalid.c3: -------------------------------------------------------------------------------- 1 | fault Error 2 | { 3 | ABC 4 | } 5 | 6 | distinct Foo1 = Error; 7 | 8 | distinct Foo3 = void; 9 | 10 | distinct Foo4 = typeid; 11 | 12 | distinct Foo = fn void(Foo** x); // #error: cannot define a new function type -------------------------------------------------------------------------------- /test/test_suite/distinct/distinct_max.c3t: -------------------------------------------------------------------------------- 1 | module test; 2 | distinct Time = long; 3 | 4 | fn void main(String[] args) 5 | { 6 | Time.min; 7 | Time.max; 8 | } -------------------------------------------------------------------------------- /test/test_suite/distinct/distinct_slicing.c3: -------------------------------------------------------------------------------- 1 | distinct Foo = double[]; 2 | 3 | fn void main() 4 | { 5 | Foo x = { 1.0, 4.5, 7.123 }; 6 | Foo y = x; 7 | Foo z = x[0:2]; 8 | Foo w = x[1..2]; 9 | double[] yekf = x[1..1]; // #error: 'Foo' to 'double[]' 10 | } 11 | -------------------------------------------------------------------------------- /test/test_suite/distinct/distinct_struct.c3: -------------------------------------------------------------------------------- 1 | 2 | struct Struct 3 | { 4 | int x; 5 | double y; 6 | } 7 | 8 | distinct Foo = Struct; 9 | 10 | struct Struct2 11 | { 12 | Foo f; 13 | int d; 14 | struct bar 15 | { 16 | Foo x; 17 | } 18 | } 19 | Foo f = { 1, 1.0 }; 20 | 21 | fn void test(int x) 22 | { 23 | Struct s = { 1, 2.0 }; 24 | Foo f2 = (Foo)(s); 25 | Foo f3 = { .x = 1 }; 26 | Struct2 s2 = { .f = { 1, 2.0 } }; 27 | Struct2 s3 = { .bar.x.y = 3.0 }; 28 | } -------------------------------------------------------------------------------- /test/test_suite/distinct/distinct_struct_array.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | distinct Foo = int; 4 | 5 | struct Struct 6 | { 7 | Foo x; 8 | int y; 9 | } 10 | 11 | distinct Struct2 = Struct; 12 | distinct StructArr = Struct2[3]; 13 | 14 | fn void test(int x) 15 | { 16 | StructArr z = { { .x = 1 }, { .y = x }, { 1, 2 }}; 17 | usz len = z.len; 18 | Foo zz = z[2].x; 19 | } 20 | -------------------------------------------------------------------------------- /test/test_suite/distinct/test_errors.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | distinct Int2 = int; 4 | 5 | fn void test() 6 | { 7 | Int2 a = 1; 8 | a = a + 1; 9 | int b; 10 | a = b; // #error: 'Int2' 11 | } -------------------------------------------------------------------------------- /test/test_suite/distinct/test_ops_on_struct.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | struct Struct 4 | { 5 | int x; 6 | double y; 7 | } 8 | 9 | distinct Foo = Struct; 10 | 11 | struct Struct2 12 | { 13 | Foo f; 14 | int d; 15 | } 16 | Foo f = { 1, 1.0 }; 17 | 18 | fn void test(int x) 19 | { 20 | Struct s = { 1, 2.0 }; 21 | Foo f2 = (Foo)(s); 22 | Foo f3 = { .x = 1 }; 23 | Struct2 s2 = { .f = { 1, 2.0 } }; 24 | } -------------------------------------------------------------------------------- /test/test_suite/dynamic/any_cast.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | interface Abc : Def 4 | {} 5 | 6 | interface Def 7 | {} 8 | 9 | fn void! test() 10 | { 11 | any x; 12 | Abc d = x; // #error: cannot implicitly be converted to 'Abc' 13 | } 14 | 15 | 16 | fn void! test2() 17 | { 18 | Abc x; 19 | any d = x; 20 | Def e = x; 21 | x = e; // #error: is not a parent interface of 'Def' 22 | } 23 | -------------------------------------------------------------------------------- /test/test_suite/dynamic/duplicate_definition.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | interface Abc 4 | { 5 | fn void abc(); 6 | fn void abc(); // #error: Duplicate definition 7 | } 8 | fn void main() 9 | { 10 | Abc* g; 11 | g.abc(); 12 | } 13 | -------------------------------------------------------------------------------- /test/test_suite/dynamic/dynamic_inherit_deep.c3t: -------------------------------------------------------------------------------- 1 | module abc; 2 | interface AstNode { 3 | fn void free(); 4 | fn double get_span(); 5 | fn void dump(int depth); 6 | } 7 | 8 | interface AstBodyStatement : AstNode { 9 | } 10 | 11 | interface AstExpression : /* AstNode,*/ AstBodyStatement { 12 | } 13 | 14 | fn void main() 15 | { 16 | AstExpression a = null; 17 | a.dump(100); 18 | } -------------------------------------------------------------------------------- /test/test_suite/dynamic/inline_protocol.c3: -------------------------------------------------------------------------------- 1 | interface Foo 2 | { 3 | fn int foo(); 4 | } 5 | 6 | struct Abc (Foo) 7 | { 8 | int a; 9 | } 10 | 11 | struct Bcd 12 | { 13 | inline Abc a; 14 | } 15 | 16 | struct Def 17 | { 18 | Abc a; 19 | } 20 | 21 | fn int Abc.foo(&self) @dynamic => 1; 22 | 23 | distinct Foob = inline Abc; 24 | 25 | fn void test1() 26 | { 27 | Foob b; 28 | Abc x; 29 | Bcd y; 30 | Def d; 31 | Foo f = &x; 32 | f = &b; 33 | f = &y; 34 | f = &d; // #error: assume the interface is implemented 35 | } -------------------------------------------------------------------------------- /test/test_suite/dynamic/same_method_twice.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::io; 3 | 4 | interface Abc 5 | { 6 | fn void test(); 7 | } 8 | 9 | fn void Abc.hello(&self) {} 10 | fn void Abc.hello(&self) {} // #error: This method is already defined 11 | 12 | fn void main() {} -------------------------------------------------------------------------------- /test/test_suite/enumerations/compile_time.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | enum MyEnum : short 3 | { 4 | HELO, 5 | WORLD, 6 | BYE 7 | } 8 | 9 | int myenum_elements = MyEnum.elements; 10 | int myenum_alignof = MyEnum.alignof; 11 | int myenum_sizeof = MyEnum.sizeof; 12 | 13 | /* #expect: compile_time.ll 14 | 15 | @compile_time.myenum_elements = local_unnamed_addr global i32 3, align 4 16 | @compile_time.myenum_alignof = local_unnamed_addr global i32 2, align 4 17 | @compile_time.myenum_sizeof = local_unnamed_addr global i32 2, align 4 -------------------------------------------------------------------------------- /test/test_suite/enumerations/enum_cast_error.c3: -------------------------------------------------------------------------------- 1 | enum Abc : char { ABC } 2 | 3 | fn void foo() 4 | { 5 | Abc x = Abc.from_ordinal(10); // #error: exceeds the max 6 | } 7 | 8 | fn void bar() 9 | { 10 | int a; 11 | Abc x = Abc.from_ordinal(a); 12 | } 13 | 14 | fn void baz() 15 | { 16 | int a; 17 | Abc x = Abc.from_ordinal(0); 18 | } 19 | 20 | fn void abc() 21 | { 22 | int a; 23 | Abc x = Abc.from_ordinal(-1); // #error: negative number 24 | } -------------------------------------------------------------------------------- /test/test_suite/enumerations/enum_invalid_param.c3: -------------------------------------------------------------------------------- 1 | enum Test : int (int kindof, int qnameof) 2 | { 3 | FOO = {1, 2} 4 | } 5 | 6 | enum Test2 : (int a, int nameof) // #error: 'nameof' is not a valid parameter name for enums 7 | { 8 | FOO = {1, 2} 9 | } 10 | 11 | enum Test3 : (int a, int ordinal) // #error: 'ordinal' is not a valid parameter name for enums 12 | { 13 | FOO = {1, 2} 14 | } 15 | -------------------------------------------------------------------------------- /test/test_suite/enumerations/enum_same_param.c3: -------------------------------------------------------------------------------- 1 | enum Test : (int a, int b) 2 | { 3 | FOO = { 1, 2 } 4 | } 5 | 6 | enum Test2 : int (int a, int a) // #error: Duplicate parameter name 'a' 7 | { 8 | FOO = { 1, 2 } 9 | } 10 | -------------------------------------------------------------------------------- /test/test_suite/enumerations/enum_with_associated_value_decl.c3: -------------------------------------------------------------------------------- 1 | enum Test2 : (usz a, usz b) { 2 | FOO = {4, 5, }, 3 | } 4 | 5 | enum Test : (usz a, usz b) { 6 | FOO = {a: 1, b: 1}, // #error: This looks like 7 | } -------------------------------------------------------------------------------- /test/test_suite/enumerations/inc_assign_fail.c3: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | import std; 4 | 5 | enum Abc 6 | { 7 | ABCD, 8 | OKFEOFKE, 9 | OFKEOFK 10 | } 11 | 12 | distinct Bob = Abc; 13 | fn void main() 14 | { 15 | Abc y; 16 | y ^= 1; // #error: Expected an integer here, not a value of type 17 | y += 1.0; // #error: The right side was 'double' 18 | Bob gh; 19 | gh += 1; // #error: A value of type 'Bob' 20 | } 21 | 22 | /* #expect: test.ll 23 | 24 | feofke -------------------------------------------------------------------------------- /test/test_suite/enumerations/inline_enum_size.c3: -------------------------------------------------------------------------------- 1 | enum Bar : inline usz 2 | { 3 | FOO, 4 | BAR, 5 | } 6 | 7 | enum Bar2 : usz (inline int x) 8 | { 9 | FOO = 1, 10 | BAR = 4, 11 | } 12 | 13 | int[Bar.BAR] x; 14 | 15 | fn int main() 16 | { 17 | char[Bar2.BAR] a; 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /test/test_suite/enumerations/missing_type.c3: -------------------------------------------------------------------------------- 1 | enum Kind : (x) // #error: A type name 2 | { 3 | FOO (10), 4 | } -------------------------------------------------------------------------------- /test/test_suite/enumerations/simple_inference.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | 3 | enum HelloEnum 4 | { 5 | HELLO, 6 | WORLD, 7 | ELLOWORLD, 8 | } 9 | fn void test() 10 | { 11 | HelloEnum h = WORLD; 12 | h = ELLOWORLD; 13 | } 14 | 15 | /* #expect: simple_inference.ll 16 | 17 | define void @simple_inference.test() #0 { 18 | entry: 19 | %h = alloca i32, align 4 20 | store i32 1, ptr %h, align 4 21 | store i32 2, ptr %h, align 4 22 | ret void 23 | } -------------------------------------------------------------------------------- /test/test_suite/errors/bitshift_failable.c3: -------------------------------------------------------------------------------- 1 | fn void test() 2 | { 3 | int! x = 0; 4 | int! z = x << 100; // #error: the bitsize of 'int' 5 | } -------------------------------------------------------------------------------- /test/test_suite/errors/else_unreachable_in_block.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std; 3 | fn void main() 4 | { 5 | char[] bytes = file::load_temp("config.json") ?? {| abort("Unable to open config.json file"); // #error: Cannot find a common type for 'char[]' and 'void' 6 | return {}; |}; // #warning: This code will never execute. 7 | char[] bytes2; 8 | } 9 | -------------------------------------------------------------------------------- /test/test_suite/errors/empty_fault.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | fault Foo 3 | { 4 | } // #error: no values -------------------------------------------------------------------------------- /test/test_suite/errors/error_decl_ok.c3: -------------------------------------------------------------------------------- 1 | module errors; 2 | 3 | fault TheError 4 | { 5 | A 6 | } 7 | 8 | fault TheError2 9 | { 10 | A, 11 | B 12 | } 13 | 14 | fault TheError3 15 | { 16 | C, D 17 | } 18 | 19 | 20 | -------------------------------------------------------------------------------- /test/test_suite/errors/error_else.c3t: -------------------------------------------------------------------------------- 1 | module foo; 2 | 3 | fault Baz 4 | { 5 | TEST 6 | } 7 | 8 | module bar; 9 | import foo; 10 | 11 | fn int! abc() 12 | { 13 | return Baz.TEST?; 14 | } 15 | 16 | module baz; 17 | import foo; 18 | 19 | fn int! abc() 20 | { 21 | return Baz.TEST?; 22 | } 23 | -------------------------------------------------------------------------------- /test/test_suite/errors/error_semantic_fails.c3: -------------------------------------------------------------------------------- 1 | fault Repeater 2 | { 3 | A, 4 | A // #error: This fault value was declared twice. 5 | } 6 | -------------------------------------------------------------------------------- /test/test_suite/errors/error_throw.c3: -------------------------------------------------------------------------------- 1 | module foo; 2 | 3 | fault Blurg 4 | { 5 | Z 6 | } 7 | 8 | fn void main() 9 | { 10 | int! i = Blurg.Z?; 11 | int! j = Blurg.Z?; 12 | } -------------------------------------------------------------------------------- /test/test_suite/errors/error_union.c3: -------------------------------------------------------------------------------- 1 | module foo; 2 | 3 | fault Blurg 4 | { 5 | X, Y, Z 6 | } 7 | 8 | fn void main() 9 | { 10 | anyfault foo; 11 | } -------------------------------------------------------------------------------- /test/test_suite/errors/invalid_cast_ct.c3: -------------------------------------------------------------------------------- 1 | module exitcodes; 2 | import std::io; 3 | 4 | fault HadError 5 | { 6 | BAD_STUFF, 7 | WORSE_STUFF, 8 | THE_WORST_STUFF 9 | } 10 | 11 | fn int main(String[] args) 12 | { 13 | HadError err = HadError.BAD_STUFF; 14 | SearchResult res = (SearchResult)(anyfault)HadError.BAD_STUFF; // #error: This expression is known at compile time 15 | return 0; 16 | } 17 | -------------------------------------------------------------------------------- /test/test_suite/errors/lone_try.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | fn void main() 4 | { 5 | try a; // #error: try? 6 | } 7 | 8 | fn void hello() 9 | { 10 | catch a; // #error: catch? 11 | } 12 | -------------------------------------------------------------------------------- /test/test_suite/errors/macro_recurse_twice.c3: -------------------------------------------------------------------------------- 1 | module oups; 2 | import std::io; 3 | 4 | fn void main() 5 | { 6 | recm(1); 7 | } 8 | 9 | macro recm(x) 10 | { 11 | recm(x + 1); // #error: Failure 12 | recm(x + 1); 13 | } -------------------------------------------------------------------------------- /test/test_suite/errors/missing_bang.c3: -------------------------------------------------------------------------------- 1 | 2 | fault Bob { FOO } 3 | 4 | fn int! test() 5 | { 6 | return Bob.FOO; // #error: You need to add a trailing 7 | } -------------------------------------------------------------------------------- /test/test_suite/errors/mixed_decl.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | fn void main() 4 | { 5 | int a, $b; 6 | int $c, $d; 7 | a++; 8 | $b++; 9 | $d++; 10 | } -------------------------------------------------------------------------------- /test/test_suite/errors/more_optional_tests.c3: -------------------------------------------------------------------------------- 1 | module foo; 2 | 3 | fault Foo { ABC } 4 | 5 | fn void test() 6 | { 7 | int x = Foo.ABC? ?? 123; 8 | } 9 | 10 | fn void test2() 11 | { 12 | int! y = Foo.ABC? ?? Foo.ABC?; 13 | } -------------------------------------------------------------------------------- /test/test_suite/errors/no_common.c3: -------------------------------------------------------------------------------- 1 | fn int! abc() 2 | { 3 | return 1; 4 | } 5 | macro test() 6 | { 7 | return @catch(abc())?; 8 | } 9 | 10 | fn void main() 11 | { 12 | test() ?? 2; // No longer an error! 13 | } -------------------------------------------------------------------------------- /test/test_suite/errors/optional_designated.c3: -------------------------------------------------------------------------------- 1 | module foo; 2 | 3 | struct Foo { int a; } 4 | struct Bar { int b; Foo f; } 5 | fn void main() 6 | { 7 | Bar { .f = Foo { foo() } }; // #error: not be discarded 8 | } 9 | 10 | fn int! foo() => 1; -------------------------------------------------------------------------------- /test/test_suite/errors/precedence_err.c3: -------------------------------------------------------------------------------- 1 | 2 | fn void test() 3 | { 4 | int x = 3 ^ 5 & 6; // #error: You need to add explicit parentheses to clarify precedence 5 | } 6 | -------------------------------------------------------------------------------- /test/test_suite/errors/rethrow_macro.c3: -------------------------------------------------------------------------------- 1 | module testing; 2 | import std::io; 3 | 4 | macro char[] read(src, Allocator allocator, n) 5 | { 6 | char* data = allocator::malloc_try(allocator, n)!; // #error: Rethrow is only allowed in macros 7 | io::read_all(src, data[:n])!; 8 | } 9 | 10 | fn void main() 11 | { 12 | ByteReader br; 13 | read(&br, allocator::temp(), 10); 14 | } -------------------------------------------------------------------------------- /test/test_suite/errors/simple_static_failable.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | 3 | module foo; 4 | 5 | fault Blurg 6 | { 7 | Y 8 | } 9 | 10 | fn void main() 11 | { 12 | static int! x = 120; 13 | int! i = Blurg.Y?; 14 | } 15 | 16 | /* #expect: foo.ll 17 | 18 | define void @foo.main() #0 { 19 | entry: 20 | %i = alloca i32, align 4 21 | %i.f = alloca i64, align 8 22 | store i64 ptrtoint (ptr @"foo.Blurg$Y" to i64), ptr %i.f, align 8 23 | ret void 24 | } -------------------------------------------------------------------------------- /test/test_suite/errors/switch_default_catch.c3: -------------------------------------------------------------------------------- 1 | fn void main() 2 | { 3 | int! x; 4 | if (catch err = x) 5 | { 6 | default: // #warning: 'if-catch' 7 | return; 8 | } 9 | return; 10 | } -------------------------------------------------------------------------------- /test/test_suite/errors/try_unwrap_using_assert.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | extern fn int! maybe(); 4 | 5 | fn int tester(int n) 6 | { 7 | int! num = maybe(); 8 | assert(try num, "Hello"); // #error: An expression was expected 9 | int x = num; 10 | return num; 11 | } 12 | -------------------------------------------------------------------------------- /test/test_suite/errors/try_with_assign_to_failable.c3: -------------------------------------------------------------------------------- 1 | fn void test() 2 | { 3 | int! z; 4 | int! w; 5 | try w = z; // #error: can only be used when unwrapping an optional 6 | } 7 | -------------------------------------------------------------------------------- /test/test_suite/errors/try_with_weird_stuff.c3: -------------------------------------------------------------------------------- 1 | fn void test1() 2 | { 3 | 4 | int! a; 5 | int b; 6 | int*! x; 7 | if (try int 1 = a) {} // #error: A new variable was expected. 8 | } 9 | 10 | fn void test2() 11 | { 12 | int! a; 13 | int b; 14 | int*! x; 15 | if (try foo::z = a, b += 1) {} // #error: The 'try' must be placed last, can you change it? 16 | } -------------------------------------------------------------------------------- /test/test_suite/expression_block/expr_block_labelled_break.c3: -------------------------------------------------------------------------------- 1 | 2 | fn void test() 3 | { 4 | for FOO: (int i = 0; i < 100; i++) 5 | { 6 | {| 7 | if (i == 10) break FOO; // #error: You cannot break out of an expression block 8 | |}; 9 | } 10 | } -------------------------------------------------------------------------------- /test/test_suite/expression_block/expr_block_no_assign.c3: -------------------------------------------------------------------------------- 1 | module helloworld; 2 | 3 | fn void main() 4 | { 5 | {| return 1; |}; // #error: which must be handled 6 | } -------------------------------------------------------------------------------- /test/test_suite/expression_block/expression_block_break.c3: -------------------------------------------------------------------------------- 1 | module fe; 2 | import std::io; 3 | extern fn int printf(char *str, ...); 4 | 5 | fn int main() 6 | { 7 | while(true) 8 | { 9 | return {| break; return 0; |}; // #error: There is no valid target for 'break', did you make a mistake 10 | } 11 | } -------------------------------------------------------------------------------- /test/test_suite/expression_block/expression_block_no_end_return.c3: -------------------------------------------------------------------------------- 1 | module foob; 2 | 3 | fn void main() 4 | { 5 | {| 6 | if (1) return 1; // #error: Expected a return statement following this statement 7 | |}; 8 | } 9 | -------------------------------------------------------------------------------- /test/test_suite/expressions/2002-02-13-ConditionalInCall.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | 3 | module test; 4 | 5 | extern fn void foo(int, double, float); 6 | 7 | fn void bar(int x) 8 | { 9 | foo(x, x ? 1.0 : 12.5, 1.0); 10 | } 11 | 12 | /* #expect: test.ll 13 | 14 | %i2b = icmp ne i32 %0, 0 15 | %ternary = select i1 %i2b, double 1.000000e+00, double 1.250000e+01 16 | call void @foo(i32 %0, double %ternary, float 1.000000e+00) 17 | -------------------------------------------------------------------------------- /test/test_suite/expressions/assign.c3: -------------------------------------------------------------------------------- 1 | fn void test1() 2 | { 3 | int* p; 4 | *p = 10; 5 | } 6 | -------------------------------------------------------------------------------- /test/test_suite/expressions/assign_deref_opt.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | fn void main() 4 | { 5 | int! a; 6 | int*! b; 7 | *b = a; // #error: You cannot assign to a dereferenced optional 8 | } 9 | 10 | -------------------------------------------------------------------------------- /test/test_suite/expressions/assign_to_address.c3: -------------------------------------------------------------------------------- 1 | // Issue #1833 2 | fn int main() 3 | { 4 | int* i; 5 | &i[0] = null; // #error: An assignable expression 6 | return 0; 7 | } -------------------------------------------------------------------------------- /test/test_suite/expressions/bit_op_on_bool.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module bitop; 3 | 4 | fn bool is_newline_codepoint(uint codepoint) { 5 | return (bool)((codepoint == 0x00_00_24_24) | (codepoint == 0x00_00_2B_92)); 6 | } 7 | 8 | /* #expect: bitop.ll 9 | 10 | %eq = icmp eq i32 %0, 9252 11 | %eq1 = icmp eq i32 %0, 11154 12 | %or = or i1 %eq, %eq1 13 | %1 = zext i1 %or to i8 14 | ret i8 %1 15 | -------------------------------------------------------------------------------- /test/test_suite/expressions/call_arg_types.c3: -------------------------------------------------------------------------------- 1 | fn void test2(ichar a) 2 | {} 3 | 4 | fn void test1() 5 | { 6 | test2(100); 7 | ichar c = 1; 8 | test2(c); 9 | 10 | int a = 1; 11 | test2(a); // #error: 'ichar' 12 | test2(100 + a); // #error: 'ichar' 13 | 14 | const int X = 120; 15 | test2(X); 16 | 17 | test2(100 + 100); // #error: '200' is out of range for 'ichar' 18 | } 19 | 20 | -------------------------------------------------------------------------------- /test/test_suite/expressions/casts/cast_const.c3: -------------------------------------------------------------------------------- 1 | fn void test1() 2 | { 3 | ichar a = (ichar)(256 + 1); 4 | ushort b = (ushort)(65536+1); 5 | ichar c = (ushort)(65536+400); // #error: truncate the value 6 | } 7 | -------------------------------------------------------------------------------- /test/test_suite/expressions/casts/cast_enum_const_to_distinct.c3: -------------------------------------------------------------------------------- 1 | enum Foo 2 | { 3 | ABC 4 | } 5 | distinct Abc = int; 6 | fn void main() 7 | { 8 | Abc d = Foo.ABC; // #error: to 'Abc' 9 | } 10 | -------------------------------------------------------------------------------- /test/test_suite/expressions/casts/cast_failable.c3: -------------------------------------------------------------------------------- 1 | fault MyErr 2 | { 3 | FOO 4 | } 5 | 6 | fn void test() 7 | { 8 | int! x = (int!)(MyErr.FOO?); // #error: Casting to an optional type is not 9 | int! y = MyErr.FOO?; 10 | } -------------------------------------------------------------------------------- /test/test_suite/expressions/casts/cast_implicit_inline_distinct.c3: -------------------------------------------------------------------------------- 1 | distinct DistinctInt = inline int; 2 | distinct DistinctInt2 = inline DistinctInt; 3 | 4 | fn void test() 5 | { 6 | DistinctInt2 y; 7 | DistinctInt x = y; 8 | DistinctInt2 z = x; // #error: Implicitly casting 9 | } -------------------------------------------------------------------------------- /test/test_suite/expressions/casts/cast_to_nonscalar.c3: -------------------------------------------------------------------------------- 1 | struct Struct 2 | { 3 | int x; 4 | } 5 | 6 | fn void test1() 7 | { 8 | int a = (Struct)(200); // #error: 'int' to 'Struct' 9 | } 10 | -------------------------------------------------------------------------------- /test/test_suite/expressions/casts/cast_unknown.c3: -------------------------------------------------------------------------------- 1 | def Number = int; 2 | 3 | fn void test1() 4 | { 5 | int a = 10; 6 | 7 | int b = (Number)(a); 8 | 9 | int c = (Foo)(a); // #error: 'Foo' could not be found 10 | } 11 | 12 | fn void test2() 13 | { 14 | int d = (Number)(bar);; // #error: 'bar' could not be found 15 | } 16 | 17 | fn void test3() 18 | { 19 | int e = (Bar)( // #error: 'Bar' could not be found 20 | faa); // #error: 'faa' could not be found 21 | } 22 | -------------------------------------------------------------------------------- /test/test_suite/expressions/casts/cast_vector_fail.c3: -------------------------------------------------------------------------------- 1 | module foo; 2 | import std; 3 | fn void test(float[<4>]* x) 4 | {} 5 | fn void test2(float[4]* x) 6 | {} 7 | 8 | fn int main(String[] args) 9 | { 10 | float[4] a; 11 | float[<4>] b; 12 | test(&a); // #error: Implicitly casting 13 | test(&b); 14 | test2(&a); 15 | test2(&b); 16 | return 1; 17 | } 18 | -------------------------------------------------------------------------------- /test/test_suite/expressions/casts/explicit_cast.c3: -------------------------------------------------------------------------------- 1 | def Number8 = char; 2 | def Number32 = int; 3 | distinct DNumber32 = int; 4 | fn void test1() 5 | { 6 | int a = (ichar)(10); 7 | int b = (ichar)(200); 8 | int c = (int)(200); 9 | ichar d = (int)(200); // #error: truncate the value 10 | } 11 | 12 | fn void test2() 13 | { 14 | char e = (Number32)(200); 15 | char f = (DNumber32)(200); // #error: DNumber32 16 | } -------------------------------------------------------------------------------- /test/test_suite/expressions/casts/failed_distinct_float_conversions.c3: -------------------------------------------------------------------------------- 1 | distinct Foo = double; 2 | distinct Bar = void*; 3 | fn int main() 4 | { 5 | float f = 1; 6 | Foo foo = f; // #error: explicit cast 7 | Bar bar = f; // #error: 'float' to 'Bar' 8 | return 1; 9 | } -------------------------------------------------------------------------------- /test/test_suite/expressions/casts/narrowing.c3: -------------------------------------------------------------------------------- 1 | fn int main() 2 | { 3 | ushort x; 4 | uint y; 5 | ushort z = x + (ushort)(0x12); 6 | return 0; 7 | } -------------------------------------------------------------------------------- /test/test_suite/expressions/casts/narrowing_through_casts.c3: -------------------------------------------------------------------------------- 1 | fn void main() 2 | { 3 | long x; 4 | 5 | int i = (char)x; // Ok 6 | char c; 7 | short s1 = (long)c; // Ok 8 | short s2 = (long)i; // #error: 'int' cannot implicitly be converted 9 | } -------------------------------------------------------------------------------- /test/test_suite/expressions/check_implict_conversion_signed_unsigned.c3t: -------------------------------------------------------------------------------- 1 | module check; 2 | 3 | fn int main() 4 | { 5 | int a = 0; 6 | ulong b = 3; 7 | b - a; 8 | return 1; 9 | } 10 | 11 | /* #expect: check.ll 12 | 13 | entry: 14 | %a = alloca i32, align 4 15 | %b = alloca i64, align 8 16 | store i32 0, ptr %a, align 4 17 | store i64 3, ptr %b, align 8 18 | %0 = load i64, ptr %b, align 8 19 | %1 = load i32, ptr %a, align 4 20 | %sext = sext i32 %1 to i64 21 | %sub = sub i64 %0, %sext 22 | ret i32 1 23 | } -------------------------------------------------------------------------------- /test/test_suite/expressions/fail_index_usize.c3: -------------------------------------------------------------------------------- 1 | fn void test(int* array, usz n) 2 | { 3 | array[n] = 33; 4 | n[array] = 33; // #error: Indexing a value of type 5 | } 6 | -------------------------------------------------------------------------------- /test/test_suite/expressions/no_valid_conversion_minus.c3: -------------------------------------------------------------------------------- 1 | struct Foo 2 | { int j; } 3 | 4 | fn int main() 5 | { 6 | int a = 0; 7 | Foo f; 8 | f - a; // #error: The subtraction 'Foo' - 'int' is not possible 9 | return 1; 10 | } -------------------------------------------------------------------------------- /test/test_suite/expressions/not_in_wrong_position.c3: -------------------------------------------------------------------------------- 1 | fn void main() 2 | { 3 | x = (a ~ a); // #error: can't appear 4 | } 5 | -------------------------------------------------------------------------------- /test/test_suite/expressions/optional_and_error.c3: -------------------------------------------------------------------------------- 1 | module testing; 2 | import std::io; 3 | 4 | fn void main() 5 | { 6 | bool ok; 7 | if (ok && !foo()) io::printfn("nok"); // #error: The expression may not be an optional 8 | } 9 | 10 | fn bool! foo() 11 | { 12 | return false; 13 | } -------------------------------------------------------------------------------- /test/test_suite/expressions/parsed_numbers.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module numbers; 3 | 4 | double a = 0x1.1p+1; 5 | double b = -12.3e-12; 6 | double c = 0x1.1p-1; 7 | double d = 12.3e+12; 8 | 9 | /* #expect: numbers.ll 10 | 11 | @numbers.a = local_unnamed_addr global double 2.125000e+00, align 8 12 | @numbers.b = local_unnamed_addr global double -1.230000e-11, align 8 13 | @numbers.c = local_unnamed_addr global double 5.312500e-01, align 8 14 | @numbers.d = local_unnamed_addr global double 1.230000e+13, align 8 -------------------------------------------------------------------------------- /test/test_suite/expressions/plus_int.c3: -------------------------------------------------------------------------------- 1 | fn void test1() 2 | { 3 | short! a = 1; 4 | @ok(+a); 5 | short b = +a; // #error: 'short!' to 'short'. 6 | } 7 | 8 | fn void test2() 9 | { 10 | int! a = 1; 11 | @ok(+a); 12 | int b = +a; // #error: 'int!' to 'int' 13 | } 14 | 15 | fn void test3() 16 | { 17 | long! a = 1; 18 | @ok(+a); 19 | long b = +a; // #error: 'long!' to 'long' 20 | } 21 | 22 | 23 | fn void test4() 24 | { 25 | int a = 1; 26 | +a = 3; // #error: An assignable expression 27 | } -------------------------------------------------------------------------------- /test/test_suite/expressions/pointer_arith.c3: -------------------------------------------------------------------------------- 1 | fn void test1(ichar* cp) 2 | { 3 | int a = 10; 4 | 5 | ichar* cp2 = cp - 10; 6 | ichar* cp3 = cp + 10; 7 | cp2 -= 10; 8 | cp2 -= a; 9 | cp3 += 10; 10 | cp3 += a; 11 | ichar* cp4 = cp - a; 12 | cp2 - cp3; 13 | } 14 | fn void test2(ichar* cp) 15 | { 16 | cp + 1; 17 | cp * 1.0; // #error: 'ichar*' by 'double' 18 | } -------------------------------------------------------------------------------- /test/test_suite/expressions/pointer_conv_error.c3: -------------------------------------------------------------------------------- 1 | fn void test1() 2 | { 3 | int myInt = 1; 4 | int* p1 = myInt; // #error: integer smaller 5 | } 6 | 7 | fn void test2() 8 | { 9 | uint myUInt = 1; 10 | int* p2 = myUInt; // #error: integer smaller 11 | } 12 | 13 | fn void test3() 14 | { 15 | uint myUInt = 1; 16 | int* p2 = (int*)(myUInt); // #error: integer smaller 17 | } 18 | 19 | -------------------------------------------------------------------------------- /test/test_suite/expressions/pointer_to_bool.c3: -------------------------------------------------------------------------------- 1 | struct Struct 2 | { 3 | char* ptr; 4 | } 5 | 6 | fn void test1(Struct* s) 7 | { 8 | if (s.ptr) {} 9 | } -------------------------------------------------------------------------------- /test/test_suite/expressions/rvalues.c3: -------------------------------------------------------------------------------- 1 | macro void hello($bar) 2 | { 3 | $bar; 4 | } 5 | const FOO = 1 + 2; 6 | fn void test() 7 | { 8 | var $Foo = int; 9 | var $Bar = $Foo; 10 | $Bar x; 11 | hello(1); 12 | var $foo = 1; 13 | $foo; 14 | FOO; 15 | } 16 | 17 | -------------------------------------------------------------------------------- /test/test_suite/expressions/simple_float_sub_neg.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module simple_float_sub_neg; 3 | 4 | fn double test(double a, double b, double c, double d) 5 | { 6 | return -(a-b) - (c-d); 7 | } 8 | 9 | /* #expect: simple_float_sub_neg.ll 10 | 11 | define double @simple_float_sub_neg.test(double %0, double %1, double %2, double %3) #0 { 12 | entry: 13 | %fsub = fsub double %0, %1 14 | %fneg = fneg double %fsub 15 | %fsub1 = fsub double %2, %3 16 | %fsub2 = fsub double %fneg, %fsub1 17 | ret double %fsub2 18 | } 19 | -------------------------------------------------------------------------------- /test/test_suite/expressions/strings.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | 4 | fn char* foo() 5 | { 6 | return "*** Word \"%s\" on line %d is not" "" ""; 7 | } 8 | 9 | /* #expect: test.ll 10 | 11 | @.str = private unnamed_addr constant [32 x i8] c"*** Word \22%s\22 on line %d is not\00" -------------------------------------------------------------------------------- /test/test_suite/expressions/ternary_no_ident.c3: -------------------------------------------------------------------------------- 1 | fn void test1() 2 | { 3 | int a = (i ? 1 : 1); // #error: 'i' could not be found, did you spell it right 4 | } 5 | 6 | fn void test2() 7 | { 8 | int a = (1 ? i : 2); // #error: 'i' could not be found, did you spell it right 9 | } 10 | 11 | fn void test3() 12 | { 13 | int a = (1 ? 2 : i); // #error: 'i' could not be found, did you spell it right 14 | } 15 | -------------------------------------------------------------------------------- /test/test_suite/expressions/test_ct_param_bug.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | macro @foo($aaa) {} 3 | fn int main(String[] args) 4 | { 5 | @foo(int); // #error: must be followed by either 6 | return 0; 7 | } -------------------------------------------------------------------------------- /test/test_suite/expressions/underscore_errors.c3: -------------------------------------------------------------------------------- 1 | fn void main() 2 | { 3 | int a = 1___0; // #error: consecutive 4 | int a = 1_0; 5 | float b = 1_0.3__4; // #error: consecutive 6 | float b = 1_0.3_4; 7 | int a2 = 0x1___0; // #error: consecutive 8 | int a2 = 0x1_0; 9 | float b2 = 0x1_0.3__4; // #error: consecutive 10 | float b2 = 0x1_0.3_4; 11 | int a3 = 0b1___0; // #error: consecutive 12 | int a3 = 0b1_0; 13 | int a3 = 0o1___0; // #error: consecutive 14 | int a3 = 0o1_0; 15 | } -------------------------------------------------------------------------------- /test/test_suite/floats/explicit_float_truncation_needed.c3: -------------------------------------------------------------------------------- 1 | fn void test() 2 | { 3 | float x = 0x7FFFFFFFFFFF.0p+400; // #error: The value '3.63419e+134' is out of range for 'float' 4 | } -------------------------------------------------------------------------------- /test/test_suite/floats/float_exceeding_size.c3: -------------------------------------------------------------------------------- 1 | fn void test() 2 | { 3 | float x = 0x7FFFFFFFFFFF.0p+40000; // #error: The float value is out of range. 4 | 5 | } -------------------------------------------------------------------------------- /test/test_suite/floats/mod.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | 3 | fn double x(double a, double b) 4 | { 5 | return a % b; 6 | } 7 | 8 | /* #expect: mod.ll 9 | 10 | define double @mod.x(double %0, double %1) #0 { 11 | entry: 12 | %fmod = frem double %0, %1 13 | ret double %fmod 14 | } -------------------------------------------------------------------------------- /test/test_suite/functions/accidental_method_1448.c3: -------------------------------------------------------------------------------- 1 | import std; 2 | def MaybeInt = maybe::Maybe(); 3 | 4 | def Func = fn void (args...); 5 | 6 | fn int main() { 7 | Func t; 8 | MaybeInt m = maybe::EMPTY(); 9 | io::printfn("%s %s", m.value, m.has_value); 10 | return 0; 11 | } -------------------------------------------------------------------------------- /test/test_suite/functions/after_vararg.c3: -------------------------------------------------------------------------------- 1 | fn void test1(int... x, int) { } // #error: A parameter name was expected 2 | fn void test2(x..., int) { } // #error: A parameter name was expected 3 | extern fn void test3(int a, ..., int y); // #error: C-style varargs cannot be followed by regular parameters. -------------------------------------------------------------------------------- /test/test_suite/functions/body_argument_fail.c3: -------------------------------------------------------------------------------- 1 | fn void foo1(int... x;) {} // #error: Expected ')' 2 | fn void foo2(... x;) {} // #error: Expected ')' 3 | fn void foo3(... x;) {} // #error: Expected ')' 4 | fn void foo4(;) {} // #error: Expected ')' 5 | fn void foo5(int x;) {} // #error: Expected ')' -------------------------------------------------------------------------------- /test/test_suite/functions/ct_named_params.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | 4 | macro foo($bar, $Type) 5 | { 6 | $Type a = $bar; 7 | return $bar; 8 | } 9 | 10 | fn void bar() 11 | { 12 | int x = foo($bar: 167, $Type: int); 13 | } 14 | 15 | /* #expect: test.ll 16 | 17 | define void @test.bar() #0 { 18 | entry: 19 | %x = alloca i32, align 4 20 | %a = alloca i32, align 4 21 | store i32 167, ptr %a, align 4 22 | store i32 167, ptr %x, align 4 23 | ret void -------------------------------------------------------------------------------- /test/test_suite/functions/default_param_fail.c3: -------------------------------------------------------------------------------- 1 | 2 | int z; 3 | 4 | fault MyError 5 | { 6 | FOO, 7 | } 8 | 9 | fn void test(int a = z) {} 10 | 11 | fn void test2(int b = MyError.FOO?) {} -------------------------------------------------------------------------------- /test/test_suite/functions/distinct_fn_ptr_and_lambda.c3t: -------------------------------------------------------------------------------- 1 | def Foo = fn void(int x); 2 | 3 | distinct Bar = Foo; 4 | 5 | fn void main() 6 | { 7 | Bar t = fn (x) { }; 8 | } -------------------------------------------------------------------------------- /test/test_suite/functions/double_return.c3: -------------------------------------------------------------------------------- 1 | module double_return; 2 | 3 | fn int test(bool pos, bool color) 4 | { 5 | return 0; 6 | return (int)(pos && color); // #warning: never execute 7 | } 8 | 9 | -------------------------------------------------------------------------------- /test/test_suite/functions/failable_param.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | fn void test4(void!); // #error: Parameters may not be optional. 4 | -------------------------------------------------------------------------------- /test/test_suite/functions/func_ptr_conversion_alias.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | 4 | def Callback = fn void(); 5 | def Callback2 = fn void(); 6 | 7 | def GetCallback = fn Callback2**[][123]*(); 8 | 9 | fn Callback**[][123]* tester() 10 | { 11 | return null; 12 | } 13 | 14 | GetCallback x = &tester; 15 | 16 | 17 | def GetCallbackOpt = fn Callback2!(); 18 | 19 | fn Callback2! tester2() => null; 20 | 21 | GetCallbackOpt y = &tester2; -------------------------------------------------------------------------------- /test/test_suite/functions/function_reserved_name.c3: -------------------------------------------------------------------------------- 1 | module arrays; 2 | 3 | import std::io; 4 | 5 | fn void double() {} // #error: reserved type name like 'double' 6 | 7 | fn void main() {} -------------------------------------------------------------------------------- /test/test_suite/functions/invalid_param.c3: -------------------------------------------------------------------------------- 1 | fn void foo(int ABC) { } // #error: Parameter names may not be all uppercase. 2 | -------------------------------------------------------------------------------- /test/test_suite/functions/macro_arguments.c3: -------------------------------------------------------------------------------- 1 | 2 | fn void foo1(int #foo) { } // #error: Only regular parameters are allowed for functions. 3 | 4 | fn void foo2(int $foo) { } // #error: Only regular parameters are allowed for functions. 5 | 6 | fn void foo3(bar) { } // #error: Only typed parameters are allowed for functions 7 | 8 | fn void foo4($Type) { } // #error: Only regular parameters are allowed for functions. 9 | 10 | fn void foo9(int x, int x) {} // #error: Duplicate parameter name 'x'. 11 | 12 | macro @foo($a, $b, $c, ...) {} -------------------------------------------------------------------------------- /test/test_suite/functions/macro_expr_type.c3: -------------------------------------------------------------------------------- 1 | macro void @foo(int #a) 2 | { 3 | } 4 | fn void main() 5 | { 6 | @foo(1.0); // #error: cannot implicitly be converted 7 | } -------------------------------------------------------------------------------- /test/test_suite/functions/missing_first_paren.c3: -------------------------------------------------------------------------------- 1 | fn void foo) // #error: Expected '(' 2 | { 3 | } 4 | -------------------------------------------------------------------------------- /test/test_suite/functions/missing_fn.c3: -------------------------------------------------------------------------------- 1 | void foo(int x) {} // #error: This looks like the beginning of a function declaration -------------------------------------------------------------------------------- /test/test_suite/functions/missing_return.c3: -------------------------------------------------------------------------------- 1 | fn int test1() // #error: Missing return statement at the end of 2 | { 3 | } -------------------------------------------------------------------------------- /test/test_suite/functions/missing_return_lambda.c3: -------------------------------------------------------------------------------- 1 | import std::io::path; 2 | 3 | fn void! process_dir(String dir_name) 4 | { 5 | path::Path p = path::temp_new(dir_name)!; 6 | path::PathWalker fnwalk = fn bool!(Path p, bool is_dir, void*) { // #error: issing return statement at the end 7 | io::printfn("path is %s", p); 8 | }; 9 | } -------------------------------------------------------------------------------- /test/test_suite/functions/naked_function.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | 3 | fn void test(int i) @naked 4 | { 5 | 6 | } 7 | 8 | /* #expect: naked_function.ll 9 | 10 | define void @naked_function.test(i32 %0) #0 { 11 | entry: 12 | ret void 13 | } 14 | 15 | attributes #0 = { naked nounwind uwtable "no-trapping-math"="true" "stack-protector-buffer-size"="8" } 16 | -------------------------------------------------------------------------------- /test/test_suite/functions/named_arg_order.c3: -------------------------------------------------------------------------------- 1 | import std; 2 | macro void test(int a, int $baz) 3 | { 4 | io::printn(a + $baz); 5 | } 6 | 7 | fn void main() 8 | { 9 | test($baz: 1, a: 4); // #error: Named arguments must always 10 | } -------------------------------------------------------------------------------- /test/test_suite/functions/param_doc_error.c3: -------------------------------------------------------------------------------- 1 | <* 2 | @param some 1 *> // #error: parameter name 3 | 4 | fn int foo(int some){ 5 | return some + 1; 6 | } 7 | 8 | <* 9 | @param some stuff *> // #error: did you forget enclosing the description in 10 | 11 | fn int foo(int some){ 12 | return some + 1; 13 | } 14 | -------------------------------------------------------------------------------- /test/test_suite/functions/param_with_comma_at_end.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | fn void foo(int a,) 4 | { 5 | 6 | } -------------------------------------------------------------------------------- /test/test_suite/functions/pointer_escape.c3: -------------------------------------------------------------------------------- 1 | int[?] foo = {1,2,3}; 2 | fn int* bar(int index) 3 | { 4 | int* array = &foo; 5 | return &array[index]; 6 | } 7 | 8 | fn int* baz(int index) 9 | { 10 | int[] array = &foo; 11 | return &array[index]; 12 | } 13 | 14 | fn int* abc(int index) 15 | { 16 | int[3] array; 17 | return &array[1]; // #error: invalid once the function returns 18 | } 19 | 20 | fn int* abc2(int index) 21 | { 22 | int val; 23 | return &val; // #error: invalid once the function returns 24 | } -------------------------------------------------------------------------------- /test/test_suite/functions/recursive_fn.c3: -------------------------------------------------------------------------------- 1 | 2 | def Foo = fn void(Foo* x); // #error: Recursive definition 3 | -------------------------------------------------------------------------------- /test/test_suite/functions/recursive_through_generic.c3: -------------------------------------------------------------------------------- 1 | module oups; 2 | import std::collections::map; 3 | 4 | fn void main() 5 | { 6 | } 7 | 8 | def FooFunc = fn void! (Bar); // #error: Recursive definition 9 | def Foo = HashMap(); 10 | 11 | struct Bar 12 | { 13 | Foo foo; 14 | } -------------------------------------------------------------------------------- /test/test_suite/functions/returning_void.c3t: -------------------------------------------------------------------------------- 1 | fn void test1() 2 | { 3 | int x; 4 | if (x == 0) return; 5 | return test1(); 6 | } 7 | /* #expect: returning_void.ll 8 | 9 | %x = alloca i32, align 4 10 | store i32 0, ptr %x, align 4 11 | %0 = load i32, ptr %x, align 4 12 | %eq = icmp eq i32 %0, 0 13 | br i1 %eq, label %if.then, label %if.exit 14 | 15 | if.then: 16 | ret void 17 | 18 | if.exit: 19 | call void @returning_void.test1() 20 | ret void 21 | -------------------------------------------------------------------------------- /test/test_suite/functions/splat_empty.c3t: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | macro foo($Type, a, ..., bool b = true, float f = 123.f) { io::printfn("%s %s %s %s", $Type.nameof, a, b, f); } 4 | macro bar($Type, a, ..., bool b, float f) { io::printfn("%s %s %s %s", $Type.nameof, a, b, f); } 5 | 6 | fn void main() 7 | { 8 | foo(void*, 99, 0, b: false, f: 456.f); // OK 9 | foo(void*, 99, /*0,*/ b: false, f: 456.f); // SEGFAULT 10 | foo(void*, 99, 0, b: false, f: 456.f); // OK 11 | bar(void*, 99, /*0,*/ b: false, f: 456.f); // SEGFAULT 12 | } -------------------------------------------------------------------------------- /test/test_suite/functions/splat_post_order.c3t: -------------------------------------------------------------------------------- 1 | macro @foo(..., bool a = true, bool b = false) 2 | { 3 | return @foo2((void*)null, $vasplat, a: a, b: b); 4 | } 5 | 6 | macro @foo2(x, ..., bool a = true, bool b = false) 7 | { } 8 | 9 | fn void main() 10 | { 11 | @foo(1, 2, 3, 4, a: true, b: false); 12 | } -------------------------------------------------------------------------------- /test/test_suite/functions/splat_raw.c3: -------------------------------------------------------------------------------- 1 | 2 | 3 | extern fn void foo(int x, ...); 4 | 5 | fn void test(void*... y) 6 | { 7 | foo(1, ...y); // #error: raw varargs 8 | } -------------------------------------------------------------------------------- /test/test_suite/functions/type_argument_live_1461.c3t: -------------------------------------------------------------------------------- 1 | module test; 2 | macro @test(uint value, #type) { 3 | 4 | } 5 | 6 | fn void main() 7 | { 8 | @test(1, uint); 9 | } 10 | -------------------------------------------------------------------------------- /test/test_suite/functions/unsplat_named.c3: -------------------------------------------------------------------------------- 1 | fn void test(int... abc, int a) 2 | { } 3 | 4 | fn void main() 5 | { 6 | int[] b = { 1, 2 }; 7 | test(...b, a: 123); 8 | } -------------------------------------------------------------------------------- /test/test_suite/functions/vaarg_raw.c3: -------------------------------------------------------------------------------- 1 | import std; 2 | 3 | fn void main() 4 | {} 5 | 6 | fn void bohoo(...) // #error: C-style variadic arguments 7 | { 8 | } -------------------------------------------------------------------------------- /test/test_suite/functions/vararg_argument_fails.c3: -------------------------------------------------------------------------------- 1 | fn void foo5(..., ...) {} // #error: Only a single variadic parameter is allowed 2 | 3 | fn void foo6(int ..., int ...) {} // #error: Only a single variadic parameter is allowed 4 | 5 | fn void foo7(int... x, int ... y) {} // #error: Only a single variadic parameter is allowed -------------------------------------------------------------------------------- /test/test_suite/functions/void_params.c3: -------------------------------------------------------------------------------- 1 | fn void test(int, void) {} // #error: Parameters may not be of type 'void'. 2 | extern fn void test3(void); // #error: C-style 'foo(void)' style argument declarations are not valid -------------------------------------------------------------------------------- /test/test_suite/generic/different_generic_def.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import test2; 3 | fn int main() 4 | { 5 | Foo1() a; 6 | return 0; 7 | } 8 | 9 | module test2(); 10 | 11 | struct Foo 12 | { 13 | Type f; 14 | } 15 | 16 | module test2(); // #error: declarations of the generic 17 | 18 | struct Foo1 19 | { 20 | Type a; 21 | } 22 | -------------------------------------------------------------------------------- /test/test_suite/generic/generic_builtin.c3t: -------------------------------------------------------------------------------- 1 | module add(); 2 | fn Type add(Type a, Type b) @builtin => 3 | a + b; 4 | 5 | module iadd; 6 | fn int iadd(int a, int b) @builtin => 7 | a + b; 8 | 9 | module main; 10 | import std::io, add, iadd; 11 | 12 | fn void main() 13 | { 14 | io::printfn("%s", iadd(1,2)); // Fine 15 | io::printfn("%s", add()(1,2)); // Error 16 | } -------------------------------------------------------------------------------- /test/test_suite/generic/generic_copy.c3t: -------------------------------------------------------------------------------- 1 | module foo(); 2 | 3 | fn void abc() 4 | { 5 | int i; 6 | defer { i++; } 7 | } 8 | 9 | module tester; 10 | import foo; 11 | 12 | def abc_my = foo::abc(); -------------------------------------------------------------------------------- /test/test_suite/generic/generic_cyclic.c3: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | import bar; 4 | 5 | def BazTest = Baz(); // #error: Recursive definition of 'BazTest' 6 | 7 | struct Test 8 | { 9 | BazTest t; 10 | } 11 | 12 | module bar(); 13 | 14 | struct Baz 15 | { 16 | Test a; 17 | } -------------------------------------------------------------------------------- /test/test_suite/generic/generic_local.c3: -------------------------------------------------------------------------------- 1 | module testing; 2 | import std::io; 3 | import foo; 4 | 5 | def Foo = foo::Foo; 6 | 7 | fn void main() 8 | { 9 | Foo f; 10 | } 11 | 12 | module foo; 13 | import foo::private; 14 | 15 | // Bug #856 16 | distinct Foo = inline PrivateFoo(); // #error: could not be found 17 | 18 | module foo::private() @local; 19 | 20 | struct PrivateFoo 21 | { 22 | Type x; 23 | } -------------------------------------------------------------------------------- /test/test_suite/generic/generic_recursion.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | import std::io; 4 | import std::collections::list; 5 | 6 | def TreeNodeList = List(); 7 | 8 | struct TreeNode 9 | { 10 | TreeNode* foo; 11 | TreeNode* bar; 12 | TreeNodeList list; 13 | } 14 | 15 | TreeNode abc; 16 | 17 | /* #expect: test.ll 18 | 19 | %TreeNode = type { ptr, ptr, %List } 20 | %List = type { i64, i64, %any, ptr } 21 | @test.abc = local_unnamed_addr global %TreeNode zeroinitializer, align 8 -------------------------------------------------------------------------------- /test/test_suite/generic/generic_with_comment.c3t: -------------------------------------------------------------------------------- 1 | module test; 2 | import generic; 3 | 4 | // Issue #1821 5 | fn void main() { 6 | Generic() asdf; 7 | } 8 | 9 | <* 10 | Hello 11 | *> 12 | module generic(); 13 | struct Generic { int a; } -------------------------------------------------------------------------------- /test/test_suite/generic/generic_without_param.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std; 3 | import abc; 4 | fn void main() 5 | { 6 | abc::test(); // #error: (<...>) 7 | } 8 | module abc(); 9 | fn void test() {} -------------------------------------------------------------------------------- /test/test_suite/generic/implicit_import_of_generic.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::io; 3 | 4 | import abc; 5 | def Def2 = Def; 6 | def Test = abc::cde::Abc(); 7 | 8 | module abc; 9 | 10 | fn void test() {} 11 | 12 | module abc::foo; 13 | 14 | struct Def { int x; } 15 | 16 | module abc::cde(); 17 | 18 | struct Abc { Type a, b; } -------------------------------------------------------------------------------- /test/test_suite/generic/incorrect_argument_type.c3: -------------------------------------------------------------------------------- 1 | module foo(); 2 | 3 | struct Foo 4 | { 5 | Type[SIZE] x; 6 | } 7 | module bar; 8 | import foo; 9 | 10 | def Bar = Foo(); // #error: Expected a value, not a type 11 | def Baz = Foo(<5, 4>); // #error: Expected a type, not a value 12 | -------------------------------------------------------------------------------- /test/test_suite/generic/used_without_param.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::collections::maybe; 3 | 4 | fn void main() 5 | { 6 | maybe::Maybe() f = Maybe {.value=6.6, .has_value=true}; // #error: Did you mean the struct 7 | maybe::Maybe()g = Maybe {.value=8, .has_value=true}; 8 | } 9 | -------------------------------------------------------------------------------- /test/test_suite/generic/used_without_param2.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::collections::maybe; 3 | 4 | fn void test() 5 | { 6 | maybe::Maybe() f = Maybe {.value=6.6, .has_value=true}; // #error: Did you mean the struct 7 | Maybe x; // #error: Did you mean the struct 8 | } 9 | 10 | -------------------------------------------------------------------------------- /test/test_suite/generic/used_without_param3.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::collections::maybe; 3 | 4 | fn void test() 5 | { 6 | maybe::Maybe() f = Maybe {.value=6.6, .has_value=true}; // #error: Did you mean the struct 7 | } -------------------------------------------------------------------------------- /test/test_suite/globals/ext_global_init.c3: -------------------------------------------------------------------------------- 1 | extern int a = 1; // #error: Extern globals may not have initializers -------------------------------------------------------------------------------- /test/test_suite/globals/extern_const.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | 4 | extern const int FOO @extern("foo1"); 5 | fn int main() 6 | { 7 | return FOO; 8 | } 9 | 10 | module bar; 11 | const int FOO @export("foo1") = 123; 12 | 13 | 14 | 15 | /* #expect: bar.ll 16 | 17 | @foo1 = local_unnamed_addr constant i32 123, align 4 -------------------------------------------------------------------------------- /test/test_suite/globals/global_align.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | 3 | module abc; 4 | 5 | int foo @align(32); 6 | 7 | fn void test() 8 | { 9 | int x = foo; 10 | } 11 | 12 | /* #expect: abc.ll 13 | 14 | @abc.foo = local_unnamed_addr global i32 0, align 32 15 | 16 | define void @abc.test() #0 { 17 | entry: 18 | %x = alloca i32, align 4 19 | %0 = load i32, ptr @abc.foo, align 32 20 | store i32 %0, ptr %x, align 4 21 | ret void 22 | } 23 | -------------------------------------------------------------------------------- /test/test_suite/globals/global_extname.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module foo; 3 | 4 | int baz @extern("foobar") = 123; 5 | 6 | /* #expect: foo.ll 7 | 8 | @foobar = local_unnamed_addr global i32 123, align 4 -------------------------------------------------------------------------------- /test/test_suite/globals/misplaced_const.c3: -------------------------------------------------------------------------------- 1 | const FOO = 3; 2 | int BAR = 4; // #error: This looks like a constant variable, did you forget 'const'? 3 | 4 | const BAZ = "ofke"; 5 | 6 | FOOBAR; // #error: Expected the start of a global declaration here -------------------------------------------------------------------------------- /test/test_suite/globals/recursive_globals.c3: -------------------------------------------------------------------------------- 1 | void *x = &x; 2 | 3 | int y = 1 + y; // #error: This looks like the initialization of the variable was circular. -------------------------------------------------------------------------------- /test/test_suite/globals/recursive_locals.c3: -------------------------------------------------------------------------------- 1 | 2 | struct List 3 | { 4 | int x; 5 | List* next; 6 | } 7 | 8 | const List A = { 7, &B }; 9 | const List B = { 8, &A }; 10 | 11 | extern List d; 12 | 13 | List c = { 7, &d }; 14 | -------------------------------------------------------------------------------- /test/test_suite/globals/self_referencing_local.c3: -------------------------------------------------------------------------------- 1 | fn void test() 2 | { 3 | void* x = &x; 4 | int y = y; // #error: This looks like the initialization of the variable was circular. 5 | } -------------------------------------------------------------------------------- /test/test_suite/globals/static_global.c3: -------------------------------------------------------------------------------- 1 | static int ifej; // #error: 'static' is only used -------------------------------------------------------------------------------- /test/test_suite/import/import_error.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::core::mem; 3 | import hello_world; // #error: No module named 4 | import test; // #error: Importing the current 5 | 6 | fn void hello() { } -------------------------------------------------------------------------------- /test/test_suite/import/import_error_multi.c3: -------------------------------------------------------------------------------- 1 | import foo, ; // #error: Another module name was expected after -------------------------------------------------------------------------------- /test/test_suite/import/import_error_string.c3: -------------------------------------------------------------------------------- 1 | import "Hello my friend"; // #error: An import should be followed by a plain identifier, not a string. Did you accidentally put the module name between ""? -------------------------------------------------------------------------------- /test/test_suite/import/import_implicit.c3: -------------------------------------------------------------------------------- 1 | module abc; 2 | 3 | struct Foo 4 | { 5 | int a; 6 | int b; 7 | } 8 | 9 | fn void test() {} 10 | 11 | module dde; 12 | 13 | fn void test() 14 | { 15 | abc::test(); // #error: Did you mean the function 'abc::test' 16 | Foo f; // #error: Did you mean the struct 'Foo' 17 | } -------------------------------------------------------------------------------- /test/test_suite/import/import_nonrecurse.c3: -------------------------------------------------------------------------------- 1 | import std::io @norecurse; 2 | fn void main() 3 | { 4 | (void)file::open("test", "r"); // #error: std::io::file::open 5 | } -------------------------------------------------------------------------------- /test/test_suite/import/import_same.c3: -------------------------------------------------------------------------------- 1 | module foo::abc; 2 | import bar; 3 | 4 | fn int test1() 5 | { 6 | return abc::test(); 7 | } 8 | 9 | module bar::abc; 10 | fn int test() { return 1; } -------------------------------------------------------------------------------- /test/test_suite/import/import_twice.c3: -------------------------------------------------------------------------------- 1 | module foo; 2 | import std::io; 3 | import std::io; // #error: imported more than 4 | 5 | fn void main() 6 | { 7 | io::printn("Hello world"); 8 | } 9 | -------------------------------------------------------------------------------- /test/test_suite/import/import_works.c3t: -------------------------------------------------------------------------------- 1 | import std::io, std::core::mem; 2 | 3 | int foo = 1; -------------------------------------------------------------------------------- /test/test_suite/initialize/init_non_resolved_type.c3: -------------------------------------------------------------------------------- 1 | const IS_ARCH_LITTLE_ENDIAN = (uint)(UIntLE{(uint)1}.val) == 1; // #error: This expression cannot be evaluated at compile time 2 | -------------------------------------------------------------------------------- /test/test_suite/initialize/initialize_bad_prio.c3: -------------------------------------------------------------------------------- 1 | 2 | fn void init1() @init("hello") // #error: Expected an integer value 3 | { 4 | } 5 | 6 | fn void init2() @init(1, 2) // #error: Too many arguments for 7 | { 8 | } 9 | 10 | fn void init3() @init(0) // #error: The priority must be a value 11 | { 12 | } 13 | 14 | fn void init4() @init(65536) // #error: The priority must be a value 15 | { 16 | } -------------------------------------------------------------------------------- /test/test_suite/initialize/initialize_jump.c3: -------------------------------------------------------------------------------- 1 | fn void foo() @init 2 | { 3 | return; // This is fine 4 | } 5 | 6 | fn int foo2() @init // #error: '@init' and '@finalizer' functions may only 7 | { 8 | return 123; 9 | } -------------------------------------------------------------------------------- /test/test_suite/initialize/initialize_parse_error.c3: -------------------------------------------------------------------------------- 1 | static foo {} ; // #error: 'static' is only used 2 | -------------------------------------------------------------------------------- /test/test_suite/initialize/initialize_prio.c3: -------------------------------------------------------------------------------- 1 | fn void test() @init() // #error: An expression was expected. 2 | { 3 | } 4 | -------------------------------------------------------------------------------- /test/test_suite/initialize/initializer_var.c3t: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | fn void init() @init 4 | { 5 | int a; 6 | a = 1; 7 | } 8 | -------------------------------------------------------------------------------- /test/test_suite/initializer_lists/disallowed_lists.c3: -------------------------------------------------------------------------------- 1 | fn void test() 2 | { 3 | char* hello = "123"; 4 | String a = { '1', '2', '3' }; 5 | char[?] b = { '1', '2', '3' }; 6 | char[3] c = { '1', '2', '3' }; 7 | char* d = { '1', '2', '3' }; // #error: Pointers cannot be initialized using an initializer list, instead you need to take the address of an array 8 | } -------------------------------------------------------------------------------- /test/test_suite/initializer_lists/indexing_into_complist.c3: -------------------------------------------------------------------------------- 1 | fn void test() 2 | { 3 | char* c = { 1, 3, "hello"}[2]; 4 | int x; 5 | } -------------------------------------------------------------------------------- /test/test_suite/initializer_lists/init_any_interface.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | interface Foo{} 4 | 5 | struct Bar (Foo) 6 | { 7 | int baz; 8 | } 9 | 10 | fn int main() { 11 | Test() a = {{}}; 12 | Test() b = {{}}; 13 | Test() a2 = {Bar{}}; // #error: It is not possible to cast 14 | 15 | return 0; 16 | } 17 | 18 | module test::generic(); 19 | 20 | struct Test 21 | { 22 | Type test; 23 | } -------------------------------------------------------------------------------- /test/test_suite/initializer_lists/initializers_to_macros.c3: -------------------------------------------------------------------------------- 1 | 2 | macro test(foo) 3 | { 4 | $typeof(foo) x = foo; 5 | } 6 | 7 | fn void main() 8 | { 9 | test(int[] { 1, 2 }); 10 | test({ 1, 2 }); // #error: It is only possible to use an untyped list as a 11 | } -------------------------------------------------------------------------------- /test/test_suite/initializer_lists/zero_inferred_array.c3: -------------------------------------------------------------------------------- 1 | fn void test() 2 | { 3 | int[?] a = {}; // #error: Zero length 4 | } -------------------------------------------------------------------------------- /test/test_suite/lambda/lambda_checks.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | def Func = fn void (bool); 3 | 4 | fn bool foo (String) => true; 5 | fn void bar(Func func) => func(false); 6 | 7 | fn void main() 8 | { 9 | Func funcX = &foo; // #error: Implicitly casting 10 | bar(&foo); // #error: Implicitly casting 11 | 12 | Func func = fn bool (String) { return true; }; // #error: which doesn't match 13 | bar(fn bool (String) { return true; }); // #error: which doesn't match 14 | } -------------------------------------------------------------------------------- /test/test_suite/lambda/var_lambda.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std; 3 | fn void main() 4 | { 5 | var x = fn int(int y) { return y * 2; }; 6 | io::printn(x(4)); 7 | io::printn(x(3)); 8 | } -------------------------------------------------------------------------------- /test/test_suite/lexing/expected_directive.c3: -------------------------------------------------------------------------------- 1 | <* 2 | @hello 3 | @param feij > 0 // #error: A string containing the description 4 | *> 5 | -------------------------------------------------------------------------------- /test/test_suite/lexing/invalid_hex_in_hexarray.c3: -------------------------------------------------------------------------------- 1 | x"abcé" // #error: This isn't a valid hexadecimal digit -------------------------------------------------------------------------------- /test/test_suite/lexing/invalid_hex_in_hexarray2.c3: -------------------------------------------------------------------------------- 1 | x"abcg" // #error: 'g' isn't a valid hexadecimal digit -------------------------------------------------------------------------------- /test/test_suite/lexing/no_builtin.c3: -------------------------------------------------------------------------------- 1 | 2 | $$1 // #error: Expected a letter after -------------------------------------------------------------------------------- /test/test_suite/literals/bad_bitwidth.c3: -------------------------------------------------------------------------------- 1 | int i = 4i15; // #error: Integer type suffix should be i8, i16, i32, i64 or i128 2 | int j = 4i1024; // #error: Integer type suffix should be i8, i16, i32, i64 or i128 3 | int k = 4i65536; // #error: Integer type suffix should be i8, i16, i32, i64 or i128 4 | int l = 4i016; // #error: Integer type suffix should be i8, i16, i32, i64 or i128 -------------------------------------------------------------------------------- /test/test_suite/literals/multi_unicode.c3: -------------------------------------------------------------------------------- 1 | int d = '\u0031\u0032\u0033\u0034'; // #error: can only contain one character -------------------------------------------------------------------------------- /test/test_suite/literals/too_small.c3: -------------------------------------------------------------------------------- 1 | char aa = 'ä'; 2 | short hmm = '謝'; // #error: unicode character -------------------------------------------------------------------------------- /test/test_suite/macro_methods/access.c3: -------------------------------------------------------------------------------- 1 | struct An1 2 | { 3 | An3 x; 4 | } 5 | 6 | struct An3 7 | { 8 | An2 y; 9 | } 10 | 11 | struct An2 12 | { 13 | int z; 14 | } 15 | 16 | extern fn void printf(char *string); 17 | 18 | macro void An2.@helloWorld(An2* &an2) 19 | { 20 | printf("An2 hello\n"); 21 | } 22 | 23 | fn void check() 24 | { 25 | printf("Checking\n"); 26 | } 27 | 28 | 29 | fn void main() 30 | { 31 | An1 an; 32 | an.x.y.@helloWorld(); 33 | An2 a; 34 | a.@helloWorld(); 35 | } -------------------------------------------------------------------------------- /test/test_suite/macro_methods/macro_method_first_param.c3: -------------------------------------------------------------------------------- 1 | 2 | struct Foo { int y; } 3 | 4 | macro Foo.text(...) => f.y; // #error: The first parameter to this method must -------------------------------------------------------------------------------- /test/test_suite/macros/hash_ident.c3: -------------------------------------------------------------------------------- 1 | macro int @cofefe(#a) 2 | { 3 | int y = 0; 4 | return #a + #a; 5 | } 6 | 7 | int abc @private = 1; 8 | 9 | fn int xx() 10 | { 11 | abc++; 12 | return abc; 13 | } 14 | 15 | fn void main() 16 | { 17 | var $x = 0; 18 | int x = 0; 19 | @cofefe(x += 1); 20 | @cofefe(xx()); 21 | $typeof($x += 1) xx; 22 | $assert $x == 1; 23 | @cofefe(y += 1); // #error: 'y' could not be found 24 | } 25 | 26 | -------------------------------------------------------------------------------- /test/test_suite/macros/implicit_return_opt.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::io; 3 | 4 | fn void main() 5 | { 6 | int x = run()!!; // #error: You cannot cast 7 | io::printfn("x=%d", x); 8 | } 9 | 10 | macro run() 11 | { 12 | int i; 13 | while (true) 14 | { 15 | i++; 16 | if (i > 10) break; 17 | if (i > 100) return IoError.EOF?; 18 | } 19 | } -------------------------------------------------------------------------------- /test/test_suite/macros/macro_always_const.c3: -------------------------------------------------------------------------------- 1 | macro bar() @const 2 | { 3 | return; // #error: provide a value 4 | } 5 | 6 | macro void barz() @const // #error: return a constant 7 | { 8 | return 1; 9 | } 10 | -------------------------------------------------------------------------------- /test/test_suite/macros/macro_body_as_value.c3: -------------------------------------------------------------------------------- 1 | macro @foo4(;@body) 2 | { 3 | @body; // #error: must be followed by () 4 | } 5 | 6 | fn void test() 7 | { 8 | @foo4() 9 | { 10 | int x = 0; 11 | }; 12 | } -------------------------------------------------------------------------------- /test/test_suite/macros/macro_body_errors.c3: -------------------------------------------------------------------------------- 1 | 2 | macro foo1(;) { } // #error: Expected an ending ')' or a block parameter on the 3 | 4 | macro foo2(;@body()) {} 5 | 6 | macro foo3(;@body) {} 7 | 8 | -------------------------------------------------------------------------------- /test/test_suite/macros/macro_body_missing_type.c3: -------------------------------------------------------------------------------- 1 | enum Foo 2 | { 3 | A, 4 | } 5 | 6 | fn void main() 7 | { 8 | @test(;$f) // #error: should be explicitly 9 | { 10 | 11 | }; 12 | } 13 | 14 | macro @test(; @body(Foo $f)) 15 | { 16 | @body(A); 17 | } -------------------------------------------------------------------------------- /test/test_suite/macros/macro_calls_prefix.c3: -------------------------------------------------------------------------------- 1 | macro foo(a, $b, $Type) {} 2 | 3 | macro @foo2(a, $b, $Type) {} 4 | 5 | macro baz(#y) {} // #error: are not allowed in function-like 6 | 7 | macro baz2(a; @body()) {} // #error: Names of macros 8 | 9 | -------------------------------------------------------------------------------- /test/test_suite/macros/macro_chained_return_void_optional.c3t: -------------------------------------------------------------------------------- 1 | module abi; 2 | 3 | fn void! abc() {} 4 | macro void! abc_macro() => abc(); 5 | 6 | fn void main() 7 | { 8 | (void)abc_macro(); 9 | } 10 | -------------------------------------------------------------------------------- /test/test_suite/macros/macro_convert_literal.c3: -------------------------------------------------------------------------------- 1 | module foo; 2 | import libc; 3 | 4 | macro foo(y) 5 | { 6 | return y * y; 7 | } 8 | 9 | fn void main() 10 | { 11 | libc::printf("%d\n", foo(10)); 12 | } -------------------------------------------------------------------------------- /test/test_suite/macros/macro_import_res_private.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module foo; 3 | fn void foo1() @private 4 | {} 5 | 6 | module bar; 7 | import foo @public; 8 | macro bar1() 9 | { 10 | foo::foo1(); 11 | } 12 | 13 | module baz; 14 | import bar; 15 | fn void test() 16 | { 17 | bar::bar1(); 18 | } 19 | 20 | /* #expect: baz.ll 21 | 22 | define void @baz.test() #0 { 23 | entry: 24 | call void @foo.foo1() 25 | ret void 26 | } -------------------------------------------------------------------------------- /test/test_suite/macros/macro_import_resolution.c3: -------------------------------------------------------------------------------- 1 | module foo; 2 | import bar; 3 | fn void run() 4 | { 5 | bar::test(); 6 | } 7 | 8 | module bar; 9 | import baz; 10 | macro test() { baz::test(); } 11 | 12 | module baz; 13 | fn void test() {} -------------------------------------------------------------------------------- /test/test_suite/macros/macro_ref_body_err1.c3: -------------------------------------------------------------------------------- 1 | 2 | macro void @bar(;@body(int &foo)) // #error: did you mean 'int*' 3 | {} 4 | 5 | -------------------------------------------------------------------------------- /test/test_suite/macros/macro_ref_body_err2.c3: -------------------------------------------------------------------------------- 1 | fn void main() 2 | { 3 | @foo(;int &foo) // #error: did you mean 'int*' 4 | { 5 | }; 6 | } 7 | 8 | macro void @foo(;@body(&foo)) 9 | { 10 | } 11 | 12 | -------------------------------------------------------------------------------- /test/test_suite/macros/macro_resolution.c3: -------------------------------------------------------------------------------- 1 | module foo; 2 | import bar; 3 | fn void run() 4 | { 5 | bar::test(); 6 | } 7 | 8 | fn void run2() 9 | { 10 | bar::test2(); 11 | } 12 | 13 | fn void tester() @private {} 14 | 15 | module bar; 16 | macro test() 17 | { 18 | tester(); // #error: 'tester' could not be found, did you spell it right 19 | } 20 | 21 | macro test2() 22 | { 23 | foo::tester(); // #error: 'foo::tester' could not be found, did you spell 24 | } 25 | -------------------------------------------------------------------------------- /test/test_suite/macros/macro_rtype.c3: -------------------------------------------------------------------------------- 1 | macro int frob() 2 | { 3 | return 0.0; // #error: int 4 | } 5 | 6 | fn void test1() 7 | { 8 | frob(); 9 | } -------------------------------------------------------------------------------- /test/test_suite/macros/macro_tagof.c3t: -------------------------------------------------------------------------------- 1 | import std::io; 2 | macro int test() @tag("hello", 1) 3 | { 4 | return 1; 5 | } 6 | 7 | fn void main() 8 | { 9 | var $v = test.tagof("hello"); 10 | io::printn($v); 11 | } -------------------------------------------------------------------------------- /test/test_suite/macros/modify_ct_param.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | macro test($baz, $Type) 4 | { 5 | $baz = 123; 6 | $Type = int; 7 | } 8 | fn void main() 9 | { 10 | var $foo = 1; 11 | $foo = 4; 12 | test(4, double); 13 | } 14 | -------------------------------------------------------------------------------- /test/test_suite/macros/ref_macro_method.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | struct MyStruct 4 | { 5 | DString* dyn; 6 | } 7 | 8 | fn void main() 9 | { 10 | @pool() 11 | { 12 | usz values_len = 10; 13 | 14 | MyStruct ms = { 15 | .dyn = mem::temp_new_array(DString, values_len).ptr, 16 | }; 17 | 18 | for (usz i; i < values_len; ++i) 19 | { 20 | ms.dyn[i].temp_init(); 21 | } 22 | 23 | ms.dyn[0].append_chars("sad"); 24 | ms.dyn[0].append("sad"); 25 | }; 26 | } -------------------------------------------------------------------------------- /test/test_suite/macros/typed_hash_access.c3: -------------------------------------------------------------------------------- 1 | 2 | macro void @foo(int #a) 3 | { 4 | var x = float.#a; // #error: cannot already be resolved 5 | } 6 | 7 | fn void main() 8 | { 9 | int inf; 10 | @foo(inf); 11 | } -------------------------------------------------------------------------------- /test/test_suite/macros/vasplat_function_call.c3: -------------------------------------------------------------------------------- 1 | import std; 2 | 3 | def IList = List(); 4 | fn IList IList.new() @operator(construct) 5 | { 6 | IList l; 7 | l.new_init($vasplat); // #error: can only be used inside 8 | return l; 9 | } 10 | 11 | 12 | fn void main() 13 | { 14 | IList a = IList.new(123, 123, 123, 123, 123, 123, 123, 134); 15 | a.push(567); 16 | 17 | io::printfn("%s", a[0]); 18 | } 19 | -------------------------------------------------------------------------------- /test/test_suite/methods/access.c3: -------------------------------------------------------------------------------- 1 | extern fn void printf(...); 2 | 3 | struct An1 4 | { 5 | An3 x; 6 | } 7 | 8 | struct An3 9 | { 10 | An2 y; 11 | } 12 | 13 | def AnCall = fn void(); 14 | 15 | struct An2 16 | { 17 | AnCall t; 18 | } 19 | 20 | fn void An2.helloWorld(An2 *an2) 21 | { 22 | printf("An2 hello\n"); 23 | } 24 | 25 | fn void check() 26 | { 27 | printf("Checking\n"); 28 | } 29 | 30 | 31 | fn void main() 32 | { 33 | An1 an; 34 | an.x.y.helloWorld(); 35 | an.x.y.t = ✓ 36 | an.x.y.t(); 37 | } -------------------------------------------------------------------------------- /test/test_suite/methods/dynamic_method_fails.c3: -------------------------------------------------------------------------------- 1 | 2 | interface Abc {} 3 | 4 | fn void any.blob(any* x) @dynamic {} // #error: 'any' may not implement 5 | fn void Abc.blob(Abc* y) @dynamic {} // #error: Interfaces may not implement 6 | fn void int.blob(int z) @dynamic {} // #error: The first parameter must always 7 | -------------------------------------------------------------------------------- /test/test_suite/methods/extension_method_check.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | def Bob = Test(); 4 | fn void Bob.crash(&self) {} 5 | 6 | fn int main() 7 | { 8 | Test() foo; 9 | return 0; 10 | } 11 | <* 12 | @require $defined(String.hash) 13 | *> 14 | module test::generic(); 15 | 16 | enum Test 17 | { 18 | ABC 19 | } -------------------------------------------------------------------------------- /test/test_suite/methods/method_extension_in_conditional_module.c3: -------------------------------------------------------------------------------- 1 | module std::core::env; 2 | const bool FOO = true; 3 | 4 | module foo @if(env::FOO); 5 | struct Foo { int a; } 6 | 7 | module bar; 8 | import std, foo; 9 | 10 | fn void Foo.baz(self) {} 11 | 12 | fn int main() 13 | { 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /test/test_suite/methods/method_name_collision.c3: -------------------------------------------------------------------------------- 1 | module testc3; 2 | 3 | fn bool any.type(self) { // #error: is not a valid method name 4 | return true; 5 | } 6 | 7 | fn void main() {} 8 | -------------------------------------------------------------------------------- /test/test_suite/methods/method_ref_for_extension_method.c3: -------------------------------------------------------------------------------- 1 | module testc3; 2 | import std::io; 3 | 4 | struct Foo { 5 | int i; 6 | } 7 | 8 | fn bool Foo[].is_empty(Foo[] array) { 9 | return array.len == 0; 10 | } 11 | 12 | def foo_arr_is_empty = Foo[].is_empty; 13 | 14 | fn void main() { 15 | Foo[] foos = { Foo { .i = 0 } }; 16 | void* foo = &Foo[].is_empty; 17 | io::printfn("Is empty: %s", foos.is_empty()); 18 | io::printfn("Is empty: %s", foo_arr_is_empty(foos)); 19 | } 20 | -------------------------------------------------------------------------------- /test/test_suite/methods/operator_defined_twice.c3: -------------------------------------------------------------------------------- 1 | distinct Foo = int; 2 | 3 | fn int Foo.fadd(&self, int x) @operator([]) { return 1; } 4 | fn int Foo.badd(&self, int x) @operator([]) { return 1; } // #error: This operator is already defined 5 | 6 | fn void main() 7 | { 8 | Foo x = 1; 9 | } 10 | -------------------------------------------------------------------------------- /test/test_suite/methods/unsupported_operator.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | fn int int.fadd(&self, int x) @operator([]) { return 1; } // #error: Only user-defined types support operator overloading -------------------------------------------------------------------------------- /test/test_suite/module/missing_semi.c3: -------------------------------------------------------------------------------- 1 | module test // #error: Expected ';' 2 | 3 | int a; -------------------------------------------------------------------------------- /test/test_suite/module/module_bad_path_ident.c3: -------------------------------------------------------------------------------- 1 | module big::MONEY; // #error: The elements of a module path must consist of only lower -------------------------------------------------------------------------------- /test/test_suite/module/module_bad_path_invalid.c3: -------------------------------------------------------------------------------- 1 | module abc::&&; // #error: Each '::' must be followed by a regular lower case sub module name -------------------------------------------------------------------------------- /test/test_suite/module/module_bad_path_keyword.c3: -------------------------------------------------------------------------------- 1 | module abc::if::while; // #error: The module path cannot contain a reserved keyword, try another name -------------------------------------------------------------------------------- /test/test_suite/module/module_error_string.c3: -------------------------------------------------------------------------------- 1 | module "Hello my friend"; // #error: 'module' should be followed by a plain identifier, not a string. Did you accidentally put the module name between ""? -------------------------------------------------------------------------------- /test/test_suite/module/module_generic_mixing.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | fn void main() {} 3 | 4 | module test(); // #error: generic 5 | fn void test() { 6 | Type a; 7 | } -------------------------------------------------------------------------------- /test/test_suite/module/module_start_bad_ident.c3: -------------------------------------------------------------------------------- 1 | module BIG::MONEY; // #error: The module name must consist of only lower case letters -------------------------------------------------------------------------------- /test/test_suite/module/module_start_invalid.c3: -------------------------------------------------------------------------------- 1 | module &&; // #error: 'module' should be followed by a module name -------------------------------------------------------------------------------- /test/test_suite/module/module_start_keyword.c3: -------------------------------------------------------------------------------- 1 | module if::hello; // #error: The module name cannot contain a reserved keyword -------------------------------------------------------------------------------- /test/test_suite/module/private_module.c3: -------------------------------------------------------------------------------- 1 | module foo @private; -------------------------------------------------------------------------------- /test/test_suite/module/unknown_modules.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | import foo; // #error: No module named 'foo' could be found 4 | import bar; // #error: No module named 'bar' could be found -------------------------------------------------------------------------------- /test/test_suite/overloading/construct_op_zero_args.c3: -------------------------------------------------------------------------------- 1 | struct Foo { int a; } 2 | fn Foo Foo.foo() @operator(construct) 3 | { 4 | return { 1 }; 5 | } 6 | -------------------------------------------------------------------------------- /test/test_suite/precedence/required_parens.c3: -------------------------------------------------------------------------------- 1 | module foo; 2 | import std::io; 3 | 4 | fn void main() 5 | { 6 | int i = 0; 7 | int j = i ^ i | i; // #error: You need to add explicit parentheses to clarify precedence. 8 | bool x = i == j == i; // #error: You need to add explicit parentheses to clarify precedence. 9 | int k = i >> j << k; // #error: You need to add explicit parentheses to clarify precedence. 10 | bool xk = i && j || i; 11 | int y = i + j + i; 12 | int yy = i * i / i + i - i; 13 | } -------------------------------------------------------------------------------- /test/test_suite/regression/crash_on_right_paren_macro.c3: -------------------------------------------------------------------------------- 1 | macro void hello($b$Bar x; // #error: Expected ')' 2 | @hello(1); 3 | var $foo = 1; 4 | $foo; 5 | FOO; 6 | } 7 | -------------------------------------------------------------------------------- /test/test_suite/slices/array_to_const_err.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std; 3 | 4 | fn void main() 5 | { 6 | char[?] z = { 1, 2 }; 7 | char[] y = z; // #error: Conversions from arrays or vectors 8 | } 9 | -------------------------------------------------------------------------------- /test/test_suite/slices/array_to_const_slice.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | module test; 3 | import std; 4 | 5 | fn void main() 6 | { 7 | char[3] $x = { 1, 2, 5 }; 8 | char[] y = $x; 9 | String $a = "hello"; 10 | char[2] $b = { 'a', 'b' }; 11 | var $c = $a +++ $b; 12 | String y2 = $c; 13 | char[] $bytes = x'0103ff'; 14 | var $d = $bytes +++ $b; 15 | char[] z = $d; 16 | } 17 | /* expect: test.ll 18 | 19 | feofke -------------------------------------------------------------------------------- /test/test_suite/slices/slice_len_error.c3: -------------------------------------------------------------------------------- 1 | int[8][8] a; 2 | fn void main() 3 | { 4 | a[2..3]; 5 | a[2:1]; 6 | a[..3]; 7 | a[2..]; 8 | a[..]; 9 | a[2:1]; 10 | a[:4]; 11 | } 12 | 13 | fn void test1() 14 | { 15 | a[:]; // #error: not elide 16 | } 17 | 18 | fn void test2() 19 | { 20 | a[2:]; // #error: not elide 21 | } -------------------------------------------------------------------------------- /test/test_suite/slices/slice_to_slice_conv_err.c3t: -------------------------------------------------------------------------------- 1 | extern fn CInt execvp(CChar* file, CChar*[] argv); 2 | 3 | fn int main() 4 | { 5 | ZString[] argv = {"ls", "-l", "-a"}; 6 | execvp((CChar*)"ls", (CChar*[])argv); 7 | return 0; 8 | } 9 | -------------------------------------------------------------------------------- /test/test_suite/slices/sub_array_init.c3: -------------------------------------------------------------------------------- 1 | fn void test2() 2 | { 3 | int[2] a = { 1, 2 }; 4 | 5 | int[2] b = 30; // #error: 'int[2]' 6 | int[2] c = a; 7 | } 8 | -------------------------------------------------------------------------------- /test/test_suite/statements/binary_fail.c3: -------------------------------------------------------------------------------- 1 | fn void test() 2 | { 3 | float a; 4 | float b; 5 | int *c; 6 | int *d; 7 | if (a + c) return; // #error: A value of type 'float' cannot be added to 'int*', an integer was expected here 8 | } -------------------------------------------------------------------------------- /test/test_suite/statements/call_missing_paren.c3: -------------------------------------------------------------------------------- 1 | fn void foo(int a) {} 2 | 3 | fn int main() 4 | { 5 | foo(10, foo(); // #error: Did you forget a ')' before this 6 | return 0; 7 | } -------------------------------------------------------------------------------- /test/test_suite/statements/conditional_return.c3: -------------------------------------------------------------------------------- 1 | fn int testReturnWithConditional() 2 | { 3 | int i = 0; 4 | if (i > 0) 5 | { 6 | return 1; 7 | } 8 | else 9 | { 10 | return 2; 11 | } 12 | } -------------------------------------------------------------------------------- /test/test_suite/statements/const_statements.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | 3 | module test; 4 | fn void main() 5 | { 6 | var $x = { { 1, 2 } }; 7 | $x; 8 | } 9 | 10 | /* #expect: test.ll 11 | 12 | define void @test.main() #0 { 13 | entry: 14 | ret void 15 | } -------------------------------------------------------------------------------- /test/test_suite/statements/default_args.c3: -------------------------------------------------------------------------------- 1 | 2 | def Foo = fn void(int a = 10); 3 | fn int abc() { return 1; } 4 | def Foo2 = fn void(int a = abc()); 5 | -------------------------------------------------------------------------------- /test/test_suite/statements/defer_test.c3: -------------------------------------------------------------------------------- 1 | fn void test() 2 | { 3 | int i = 0; 4 | defer 5 | { 6 | i = i + 1; 7 | } 8 | return; 9 | } -------------------------------------------------------------------------------- /test/test_suite/statements/do_without_compound.c3: -------------------------------------------------------------------------------- 1 | fn void test1() 2 | { 3 | do test1(); while(1); // #error: A do loop must use { } around its body 4 | } 5 | 6 | -------------------------------------------------------------------------------- /test/test_suite/statements/for.c3: -------------------------------------------------------------------------------- 1 | module for_test; 2 | 3 | 4 | 5 | fn int test1() 6 | { 7 | for (int x = 0;;) 8 | { 9 | } 10 | } 11 | 12 | fn int test2() 13 | { 14 | for (int x = 0; 1 ;) 15 | { 16 | } 17 | } 18 | 19 | fn int test3() 20 | { 21 | for (; 1 ;2) 22 | { 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /test/test_suite/statements/for_empty.c3: -------------------------------------------------------------------------------- 1 | fn int test1() 2 | { 3 | for (;;); 4 | } 5 | fn int test2() 6 | { 7 | for (;;) {} 8 | } 9 | -------------------------------------------------------------------------------- /test/test_suite/statements/for_errors.c3: -------------------------------------------------------------------------------- 1 | fn void foo() {} 2 | 3 | fn int main() 4 | { 5 | for (; foo() ; ) {} // #error: Expected a boolean expression 6 | return 0; 7 | } -------------------------------------------------------------------------------- /test/test_suite/statements/for_statement_placement.c3: -------------------------------------------------------------------------------- 1 | fn void test(int x) 2 | {} 3 | 4 | fn void main() 5 | { 6 | for (int i = 0; i < 10; i++) test( 7 | i 8 | ); 9 | for (int i = 0; i < 10; i++) 10 | test( // #error: A single statement after 11 | i 12 | ); 13 | } -------------------------------------------------------------------------------- /test/test_suite/statements/for_with_extra_declarations.c3: -------------------------------------------------------------------------------- 1 | fn void test() 2 | { 3 | int j; 4 | for (int i = 0; i < 10; i++) 5 | { 6 | 7 | } 8 | for (int i = 0, int foo = 0; i < 10; i++) 9 | { 10 | 11 | } 12 | 13 | for (int i = 0, j = 1; i < 10; i++, j++) 14 | { 15 | 16 | } 17 | } -------------------------------------------------------------------------------- /test/test_suite/statements/foreach_custom_errors.c3: -------------------------------------------------------------------------------- 1 | fn void test1() 2 | { 3 | int x; 4 | foreach (a : x) { }; // #error: It's not possible to enumerate an expression of type 'int' 5 | } 6 | 7 | distinct Test1 = int; 8 | 9 | fn void test2() 10 | { 11 | Test1 x; 12 | foreach (a : x) { }; // #error: It's not possible to enumerate an expression of type 'Test1' 13 | } 14 | 15 | 16 | -------------------------------------------------------------------------------- /test/test_suite/statements/foreach_distinct_pointer_1506.c3: -------------------------------------------------------------------------------- 1 | distinct Type = char*; 2 | fn usz Type.len(str) 3 | { 4 | return 0; 5 | } 6 | fn int main(String[] args) 7 | { 8 | Type x = "AAAAA"; // Or ZString 9 | foreach(y : x) // #error: It's not possible to enumerate an expression 10 | { 11 | 12 | } 13 | return 0; 14 | } -------------------------------------------------------------------------------- /test/test_suite/statements/foreach_parse_error.c3: -------------------------------------------------------------------------------- 1 | fn void test9() 2 | { 3 | foreach (int a : { [2] = 1 }) foo(); 4 | foreach (int a : { [2] = 2, 1 }) foo(); // #error: Normal initialization cannot be mixed with designated initialization. 5 | } -------------------------------------------------------------------------------- /test/test_suite/statements/foreach_r_custom_errors.c3: -------------------------------------------------------------------------------- 1 | fn void test1() 2 | { 3 | int x; 4 | foreach_r (a : x) { }; // #error: It's not possible to enumerate an expression of type 'int' 5 | } 6 | 7 | distinct Test1 = int; 8 | 9 | fn void test2() 10 | { 11 | Test1 x; 12 | foreach_r (a : x) { }; // #error: It's not possible to enumerate an expression of type 'Test1' 13 | } 14 | 15 | 16 | -------------------------------------------------------------------------------- /test/test_suite/statements/foreach_r_parse_error.c3: -------------------------------------------------------------------------------- 1 | fn void test9() 2 | { 3 | foreach_r (int a : { [2] = 1 }) foo(); 4 | foreach_r (int a : { [2] = 2, 1 }) foo(); // #error: Normal initialization cannot be mixed with designated initialization. 5 | } -------------------------------------------------------------------------------- /test/test_suite/statements/foreach_r_with_error.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | fn void test() 4 | { 5 | int[3]! x; 6 | int g; 7 | foreach_r (z : x) // #error: The foreach iterable expression may not be 8 | { 9 | g += z; 10 | x[0] = 1; 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /test/test_suite/statements/foreach_with_error.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | fn void test() 4 | { 5 | int[3]! x; 6 | int g; 7 | foreach (z : x) // #error: The foreach iterable expression 8 | { 9 | g += z; 10 | x[0] = 1; 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /test/test_suite/statements/foreach_wrong_index.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | struct Foo 4 | { 5 | int[3] elements; 6 | } 7 | 8 | fn int Foo.at(Foo *vector, float index) @operator([]) 9 | { 10 | return 1; 11 | } 12 | 13 | fn int Foo.len(Foo *vector) @operator(len) 14 | { 15 | return 3; 16 | } 17 | 18 | fn void main() 19 | { 20 | 21 | Foo f; 22 | io::printfn("%s", f[12.2]); 23 | foreach (int i, value : f) // #error: Only integer 24 | { 25 | io::printfn("v[%s] = %s", i, value); 26 | } 27 | } -------------------------------------------------------------------------------- /test/test_suite/statements/if_decl.c3: -------------------------------------------------------------------------------- 1 | fn int main() 2 | { 3 | if (int a) {} // #error: Expected a declaration with initializer 4 | return 0; 5 | } 6 | -------------------------------------------------------------------------------- /test/test_suite/statements/label_errors.c3: -------------------------------------------------------------------------------- 1 | 2 | fn int main() 3 | { 4 | do FOO: 5 | { 6 | while FOO: (1) // #error: would shadow a previous declaration 7 | { 8 | return 1; 9 | } 10 | }; 11 | return 0; 12 | } 13 | 14 | 15 | fn void test1() 16 | { 17 | do FOO: 18 | { 19 | while (1) 20 | { 21 | break BAR; // #error: A labelled statement with the name 'BAR' can't be found in the current scope 22 | } 23 | }; 24 | } -------------------------------------------------------------------------------- /test/test_suite/statements/nextcase_missing_case.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::io; 3 | 4 | fn void main() 5 | { 6 | int a; 7 | switch (a) 8 | { 9 | case 1: 10 | nextcase 0; // #error: There is no 'case 0' 11 | default: 12 | 13 | } 14 | } -------------------------------------------------------------------------------- /test/test_suite/statements/nextcase_no_switch.c3: -------------------------------------------------------------------------------- 1 | fn void main() 2 | { 3 | int x = 0; 4 | switch 5 | { 6 | case true: 7 | nextcase false; // #error: cannot be used with 8 | default: 9 | break; 10 | } 11 | } -------------------------------------------------------------------------------- /test/test_suite/statements/return_stmt.c3: -------------------------------------------------------------------------------- 1 | fn void testNoReturn() 2 | { 3 | int i = 0; 4 | i = -i; 5 | } 6 | 7 | fn int testReturn() 8 | { 9 | int i = 0; 10 | return i; 11 | } -------------------------------------------------------------------------------- /test/test_suite/statements/return_with_other_at_end.c3: -------------------------------------------------------------------------------- 1 | fn int testReturnWithOtherAtEnd() 2 | { 3 | int i = 0; 4 | return i; 5 | if (i == 10) i++; // #warning: This code will 6 | i = i + 2; 7 | } 8 | -------------------------------------------------------------------------------- /test/test_suite/statements/switch_error_fallthrough.c3: -------------------------------------------------------------------------------- 1 | fn int main() 2 | { 3 | int a; 4 | switch (a) 5 | { 6 | case 1: // #error: Fallthrough cases 7 | // ... 8 | case 2: 9 | } 10 | return 0; 11 | } -------------------------------------------------------------------------------- /test/test_suite/statements/switch_error_range.c3: -------------------------------------------------------------------------------- 1 | module foo; 2 | 3 | fn void test() 4 | { 5 | int i; 6 | switch (i) 7 | { 8 | case 15..13: // #error: The range is not valid because the first value (15) is greater than the second (13) 9 | i++; 10 | return; 11 | } 12 | } -------------------------------------------------------------------------------- /test/test_suite/statements/while_statement_placement.c3: -------------------------------------------------------------------------------- 1 | fn void test1() 2 | { 3 | int a; 4 | while (1) a++; 5 | while (1) 6 | { 7 | a++; 8 | } 9 | while (1) 10 | a++; // #error: must be placed on the same line 11 | } -------------------------------------------------------------------------------- /test/test_suite/stdlib/minmax.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | fn void main() 4 | { 5 | io::printfn("min(-1, 1) == %s", min(-1, 1)); 6 | io::printfn("max(-1, 1) == %s", max(-1, 1)); 7 | io::printfn("min(-1, 0, 1) == %s", min(-1, 0, 1)); 8 | io::printfn("max(-1, 0, 1) == %s", max(-1, 0, 1)); 9 | } 10 | -------------------------------------------------------------------------------- /test/test_suite/strings/literal_hex_ok.c3: -------------------------------------------------------------------------------- 1 | char bar1 = '\xaf'; 2 | ichar bar2 = '\x0F'; 3 | ushort bar4 = '\u0FaF'; 4 | -------------------------------------------------------------------------------- /test/test_suite/strings/string_escape.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | fn void main() 3 | { 4 | char *s = "Hello\0 world!" " now"; 5 | } 6 | 7 | /* #expect: string_escape.ll 8 | 9 | @.str = private unnamed_addr constant [18 x i8] c"Hello\00 world! now\00", align 1 10 | 11 | define void @string_escape.main() #0 { 12 | entry: 13 | %s = alloca ptr, align 8 14 | store ptr @.str, ptr %s, align 8 15 | ret void 16 | } 17 | 18 | define i32 @main(i32 %0, ptr %1) #0 { 19 | entry: 20 | call void @string_escape.main() 21 | ret i32 0 22 | } -------------------------------------------------------------------------------- /test/test_suite/strings/string_len.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | 3 | int i = "123".len; 4 | 5 | /* #expect: string_len.ll 6 | 7 | @string_len.i = local_unnamed_addr global i32 3, align 4 -------------------------------------------------------------------------------- /test/test_suite/struct/const_access_error.c3: -------------------------------------------------------------------------------- 1 | 2 | fn void main() 3 | { 4 | int x; 5 | x.""; // #error: Expected an identifier here 6 | } -------------------------------------------------------------------------------- /test/test_suite/struct/flex_array_comparison.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | struct Abc 4 | { 5 | int x; 6 | int[?] y; 7 | } 8 | 9 | 10 | fn void test() 11 | { 12 | Abc x; 13 | Abc y; 14 | bool same = x.y == y.y; // #error: does not support comparisons 15 | } -------------------------------------------------------------------------------- /test/test_suite/struct/flexible_array_resolve.c3: -------------------------------------------------------------------------------- 1 | struct Abc 2 | { 3 | Foo[4] x; // #error: Arrays of structs with flexible array members 4 | } 5 | 6 | struct Foo 7 | { 8 | int a; 9 | int[?] x; 10 | } 11 | 12 | struct Foo2 13 | { 14 | int a; 15 | int[?] x, y; // #error: must be the last element 16 | } 17 | -------------------------------------------------------------------------------- /test/test_suite/struct/func_return_struct.c3: -------------------------------------------------------------------------------- 1 | struct Test 2 | { 3 | int i; 4 | short s1, s2; 5 | } 6 | 7 | extern fn Test func_returning_struct(); 8 | 9 | fn void loop() 10 | { 11 | func_returning_struct(); 12 | } 13 | -------------------------------------------------------------------------------- /test/test_suite/struct/inner_struct_name.c3: -------------------------------------------------------------------------------- 1 | struct Foo { 2 | union Bar { // #error: name of an inner struct 3 | int a; 4 | } 5 | } 6 | -------------------------------------------------------------------------------- /test/test_suite/struct/recursive_structs.c3: -------------------------------------------------------------------------------- 1 | struct Test1 2 | { 3 | Test1 *x; 4 | } 5 | 6 | struct Test2 7 | { 8 | Test2[] y; 9 | } 10 | 11 | struct Test3 // #error: Recursive definition 12 | { 13 | Test3[4] z; 14 | } 15 | 16 | struct Test4 17 | { 18 | Test4[3]* w; 19 | } 20 | 21 | 22 | struct Test5 23 | { 24 | Test5[3][] w; 25 | } 26 | -------------------------------------------------------------------------------- /test/test_suite/struct/simple_struct.c3t: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | Foo a @private; 4 | 5 | struct Foo 6 | { 7 | int x; 8 | double a; 9 | } 10 | 11 | /* #expect: test.ll 12 | 13 | %Foo = type { i32, double } 14 | @test.a = internal unnamed_addr global %Foo zeroinitializer, align 8 -------------------------------------------------------------------------------- /test/test_suite/struct/sret.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | struct Abc 3 | { 4 | long a; 5 | long b; 6 | long c; 7 | long d; 8 | long e; 9 | } 10 | 11 | extern fn Abc foo1(); 12 | extern fn Abc foo2(); 13 | 14 | fn void bar() 15 | { 16 | Abc dummy1 = foo1(); 17 | Abc dummy2 = foo2(); 18 | } 19 | 20 | 21 | /* #expect: sret.ll 22 | 23 | sret(%Abc) 24 | sret(%Abc) 25 | sret(%Abc) 26 | sret(%Abc) -------------------------------------------------------------------------------- /test/test_suite/struct/struct_bad_member.c3: -------------------------------------------------------------------------------- 1 | struct Foo { 2 | void bar; // #error: Members cannot be of 3 | } 4 | 5 | def Void = void; 6 | struct Foo2 { 7 | Void bar; // #error: Members cannot be of 8 | } 9 | 10 | distinct Void2 = void; 11 | struct Foo3 { 12 | Void2 bar; // #error: has unknown size 13 | } 14 | 15 | fn void main(String[] args) { 16 | Foo foo; 17 | Foo2 foo2; 18 | Foo3 foo3; 19 | } 20 | -------------------------------------------------------------------------------- /test/test_suite/struct/struct_comma.c3: -------------------------------------------------------------------------------- 1 | import std::io; 2 | 3 | struct Test 4 | { 5 | int a, // #error: Did you accidentally use ',' 6 | int b, 7 | } 8 | -------------------------------------------------------------------------------- /test/test_suite/struct/struct_params.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | struct Foo 4 | { 5 | char p; 6 | short q; 7 | char r; 8 | int x; 9 | short y, z; 10 | int q2; 11 | } 12 | 13 | extern fn int test(Foo, float); 14 | extern fn int testE(char,short,char,int,int,float); 15 | 16 | fn void test3(Foo *x) 17 | { 18 | x.q = 1; 19 | } 20 | 21 | fn void test2(Foo y) 22 | { 23 | testE(y.p, y.q, y.r, y.x, y.y, 0.1); 24 | test(y, 0.1); 25 | test2(y); 26 | test3(&y); 27 | } 28 | -------------------------------------------------------------------------------- /test/test_suite/struct/zero_member.c3: -------------------------------------------------------------------------------- 1 | def Foo = int[0]; // #error: An array may not have zero 2 | 3 | struct Bar 4 | { 5 | Foo x; 6 | int b; 7 | } -------------------------------------------------------------------------------- /test/test_suite/switch/bad_ranges.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | fn void! test1() 4 | { 5 | double a; 6 | switch (a) 7 | { 8 | case 1.3 .. 4.5: // #error: Ranges must be constant integers 9 | default: 10 | } 11 | } 12 | 13 | fn void! test2() 14 | { 15 | int a; 16 | switch (a) 17 | { 18 | case 2 .. 3: 19 | case a .. 3: // #error: Ranges must be constant integers 20 | default: 21 | } 22 | } -------------------------------------------------------------------------------- /test/test_suite/switch/failable_switch.c3: -------------------------------------------------------------------------------- 1 | fault MyError 2 | { 3 | FOO 4 | } 5 | 6 | fn void test() 7 | { 8 | int x = 0; 9 | switch (x) 10 | { 11 | case MyError.FOO? : // #error: 'int!' to 'int' 12 | x = x + 1; 13 | } 14 | } -------------------------------------------------------------------------------- /test/test_suite/symbols/allow_local_shadowing.c3: -------------------------------------------------------------------------------- 1 | int foo; 2 | 3 | fn void x() 4 | { 5 | double foo = 123; 6 | } 7 | 8 | fn void y(int foo) 9 | { 10 | } -------------------------------------------------------------------------------- /test/test_suite/symbols/shadow_struct.c3: -------------------------------------------------------------------------------- 1 | struct Foo 2 | { 3 | Foo *x; 4 | int y; 5 | } 6 | 7 | def Foo = float; // #error: shadow a previous declaration 8 | 9 | enum Bar 10 | { 11 | TEST1, 12 | TEST2 13 | } 14 | 15 | def Bar = float; // #error: shadow a previous declaration -------------------------------------------------------------------------------- /test/test_suite/types/enum_illegal_type.c3: -------------------------------------------------------------------------------- 1 | enum EnumTestErrorType : float // #error: must be an integer type not 'float' 2 | { 3 | VALUE_BOOM 4 | } 5 | 6 | enum EnumWithErrorType2 : int* // #error: must be an integer type not 'int*' 7 | { 8 | TEST 9 | } -------------------------------------------------------------------------------- /test/test_suite/types/enum_ok.c3: -------------------------------------------------------------------------------- 1 | enum EnumTest : long 2 | { 3 | VALUE1, 4 | VALUE2 5 | } 6 | 7 | def Frob = long; 8 | 9 | enum EnumTestAlias : Frob 10 | { 11 | VALUE1, 12 | VALUE2 13 | } 14 | 15 | enum EnumTestDefault 16 | { 17 | VALUE, 18 | VALUE2 19 | } 20 | 21 | 22 | enum EnumWithErrorData2 : int (int bar,) 23 | { 24 | TEST // #error: associated value 25 | } 26 | 27 | enum EnumTestErrorType4 28 | { 29 | } 30 | 31 | enum EnumTest5 32 | { 33 | B, 34 | C, 35 | } -------------------------------------------------------------------------------- /test/test_suite/types/enum_param.c3: -------------------------------------------------------------------------------- 1 | enum Foo 2 | { 3 | A, B 4 | } 5 | 6 | fn void test(Foo f) 7 | {} 8 | 9 | fn void test2() 10 | { 11 | test(Foo.A); 12 | } -------------------------------------------------------------------------------- /test/test_suite/types/enum_parse_errors.c3: -------------------------------------------------------------------------------- 1 | 2 | enum EnumWithErrorWithMissingName : (int) // #error: Expected a member name here 3 | { 4 | TEST 5 | } 6 | 7 | enum EnumWithErrorData : ( int 8 | { // #error: Expected a member name here 9 | TEST 10 | } 11 | 12 | enum EnumWithErrorData2 : ( int, int bar ) // #error: Expected a member name here 13 | { 14 | TEST 15 | } 16 | 17 | 18 | enum EnumTestErrorType3 : int 19 | { 20 | A, 21 | A // #error: This enum constant is declared twice 22 | } -------------------------------------------------------------------------------- /test/test_suite/types/illegal_array_size_constant.c3: -------------------------------------------------------------------------------- 1 | module testing; 2 | 3 | struct Foo 4 | { 5 | Entry[1 << N] data; // #error: 'N' could not be found 6 | } 7 | 8 | struct Entry 9 | { 10 | String key; 11 | String value; 12 | } -------------------------------------------------------------------------------- /test/test_suite/types/non_rec_fn.c3: -------------------------------------------------------------------------------- 1 | 2 | def BlahFn = fn int(Foo f); 3 | def FooFn = fn int(Foo f, int j); 4 | struct Foo 5 | { 6 | BlahFn x; 7 | FooFn okf; 8 | } 9 | 10 | 11 | Foo g; -------------------------------------------------------------------------------- /test/test_suite/types/recursive_array.c3: -------------------------------------------------------------------------------- 1 | struct Qq 2 | { 3 | Qq[3]* a; 4 | } -------------------------------------------------------------------------------- /test/test_suite/types/recursive_fn.c3: -------------------------------------------------------------------------------- 1 | def BlahFn = fn int(BlahFn f); // #error: Recursive definition of 'BlahFn' -------------------------------------------------------------------------------- /test/test_suite/types/recursive_typedef.c3: -------------------------------------------------------------------------------- 1 | def Number2 = Number1; // #error: Recursive definition of 'Number2' 2 | def Number1 = Number2; 3 | 4 | def Number = Number; // #error: Recursive definition of 'Number' 5 | 6 | 7 | def Loop2 = Loop; // #error: Recursive definition of 'Loop2' 8 | def Loop3 = Loop2; 9 | def Loop = Loop3; 10 | -------------------------------------------------------------------------------- /test/test_suite/types/redefinition.c3: -------------------------------------------------------------------------------- 1 | def Number = int; 2 | def Number = uint; // #error: 'Number' would shadow a previous declaration. -------------------------------------------------------------------------------- /test/test_suite/types/typedefs.c3: -------------------------------------------------------------------------------- 1 | def Arr = int[4]; 2 | 3 | Arr a = { 3, 4, 5, 6 }; 4 | 5 | fn void test1() 6 | { 7 | Arr b = { 3, 4, 5, 6 }; 8 | int c = b; // #error: 'Arr' (int[4]) to 'int' 9 | int d = a; // #error: 'Arr' (int[4]) to 'int' 10 | } 11 | 12 | -------------------------------------------------------------------------------- /test/test_suite/types/various.c3: -------------------------------------------------------------------------------- 1 | func1 a = 1; // #error: The name of a type 2 | 3 | fn void func1() {} 4 | 5 | uint b = -1; -------------------------------------------------------------------------------- /test/test_suite/unicode/commenting-out.c3: -------------------------------------------------------------------------------- 1 | // #error: Invalid encoding - Unbalanced bidirectional markers. 2 | int main() { 3 | bool isAdmin = false; 4 | /*‮ } ⁦if (isAdmin)⁩ ⁦ begin admins only */ 5 | printf("You are an admin.\n"); 6 | /* end admins only ‮ { ⁦*/ 7 | return 0; 8 | } 9 | 10 | 11 | -------------------------------------------------------------------------------- /test/test_suite/union/flexible_array_union.c3: -------------------------------------------------------------------------------- 1 | union Zee 2 | { 3 | int z; 4 | int[?] y; // #error: Flexible array members not allowed in unions. 5 | } -------------------------------------------------------------------------------- /test/test_suite/union/inferred_size_vector.c3: -------------------------------------------------------------------------------- 1 | union Foo 2 | { 3 | int[] x; // #error: Inferred vector types can only 4 | } 5 | -------------------------------------------------------------------------------- /test/test_suite/union/test_unions.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | union Qu 4 | { 5 | Qu *x; 6 | } 7 | 8 | union Xe 9 | { 10 | char c; 11 | int a, z; 12 | long b; 13 | void *b1; 14 | struct qu 15 | { 16 | int a; 17 | long z; 18 | } 19 | } 20 | 21 | fn Xe foo(Xe a) 22 | { 23 | a.c = 123; 24 | a.a = 39249; 25 | a.b = 12301230123123i64; 26 | a.z = 1; 27 | return a; 28 | } -------------------------------------------------------------------------------- /test/test_suite/union/union_member_voidcast.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | union Xu 4 | { 5 | void *b; 6 | } 7 | 8 | fn Xu foo() 9 | { 10 | Xu a; 11 | a.b = (void*)(123); 12 | return a; 13 | } -------------------------------------------------------------------------------- /test/test_suite/union/union_zero.c3: -------------------------------------------------------------------------------- 1 | union Abs // #error: Zero sized unions 2 | { 3 | } -------------------------------------------------------------------------------- /test/test_suite/variables/const_in_func.c3t: -------------------------------------------------------------------------------- 1 | // #target: linux-x64 2 | module scratch; 3 | import std::test; 4 | fn void main() 5 | { 6 | int x = test::abc(); 7 | } 8 | 9 | module std::test; 10 | 11 | macro abc() 12 | { 13 | const int A = 256; 14 | return A; 15 | } 16 | 17 | /* #expect: scratch.ll 18 | 19 | @main.A = internal local_unnamed_addr constant i32 256, align 4 -------------------------------------------------------------------------------- /test/test_suite/variables/consts.c3: -------------------------------------------------------------------------------- 1 | const int foo = 3; // #error: must be all uppercase 2 | 3 | fn void foo(int i) 4 | { 5 | const int x = i; // #error: must be all uppercase 6 | const int Y = i; 7 | } -------------------------------------------------------------------------------- /test/test_suite/variables/var_init.c3t: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | struct Abc 4 | { 5 | int[100] x; 6 | } 7 | 8 | 9 | fn void main() 10 | { 11 | int z @noinit; 12 | Abc y @noinit; 13 | int x; 14 | Abc w; 15 | } 16 | 17 | /* #expect: test.ll 18 | 19 | entry: 20 | %z = alloca i32, align 4 21 | %y = alloca %Abc, align 4 22 | %x = alloca i32, align 4 23 | %w = alloca %Abc, align 4 24 | store i32 0, ptr %x, align 4 25 | call void @llvm.memset.p0.i64(ptr align 4 %w, i8 0, i64 400, i1 false) 26 | ret void 27 | -------------------------------------------------------------------------------- /test/test_suite/vector/swizzling.c3: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | 3 | fn void! swizzle_test() 4 | { 5 | int[<4>] abc = { 1, 2, 3, 4 }; 6 | int[<3>] z = abc.rbx; // #error: Mixing 7 | int[<2>] gh; 8 | int[<2>] uh = gh.xz; // #error: component is not present 9 | 10 | } 11 | 12 | 13 | 14 | fn int main() 15 | { 16 | int[<2>] $test = {3, 3}; 17 | int[<2>] $test2 = {4, 4}; 18 | $if ($test2.x != $test.x): 19 | y++; // #error: did you spell it 20 | $endif 21 | return 0; 22 | } -------------------------------------------------------------------------------- /test/test_suite/vector/vector_conversion_scalar.c3: -------------------------------------------------------------------------------- 1 | fn void test2(int[<2>] x) {} 2 | fn void main() 3 | { 4 | int[<2>] y = 1; 5 | y[..] = 3; 6 | y.xy = 3; // #error: cannot use swizzling 7 | y *= 2; 8 | y = 3; // #error: explicit cast 9 | test2(3); // #error: explicit cast 10 | {| 11 | if (y[0] == 3) return 1; // #error: explicit cast 12 | return y; 13 | |}; 14 | } -------------------------------------------------------------------------------- /test/test_suite/vector/vector_lowering_regression1.c3t: -------------------------------------------------------------------------------- 1 | // #target: linux-x64 2 | module test; 3 | union Vec4f @export @align(16) { 4 | struct { float x,y,z,w; } 5 | float[<4>] v; 6 | } 7 | 8 | extern fn void foo(Vec4f) @extern("foo"); 9 | 10 | /* #expect: test.ll 11 | 12 | declare void @foo(double, double) #0 -------------------------------------------------------------------------------- /test/test_suite/vector/vector_pointer_errors.c3: -------------------------------------------------------------------------------- 1 | module vecpointer; 2 | 3 | fn void pointer_add_sub_diff() 4 | { 5 | int[5] a; 6 | int*[<2>] y; 7 | double*[<2>] z = y; // #error: 'int*[<2>]' to 'double*[<2>]' 8 | y / y; // #error: Cannot divide 9 | y % y; // #error: not defined 10 | y * y; // #error: multiply 11 | y ^ y; // #error: not defined 12 | iptr[<2>] g = (iptr[<2>])y; 13 | g | g; 14 | } 15 | -------------------------------------------------------------------------------- /test/test_suite/vector/vector_to_array_fail.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | import std::io; 3 | fn void main() 4 | { 5 | int[<2>] x = { 4, 7 }; 6 | int[2] y = x; 7 | int[?] y1 = y; 8 | int[?] y2 = x; 9 | int[] z = x; 10 | int[] w = y; 11 | double[<2>] ww = x; 12 | short[<2>] www = y; // #error: Implicitly casting 'int[2]' to 'short[<2>]' 13 | } -------------------------------------------------------------------------------- /test/test_suite/vector/vector_to_vector_const_fail.c3: -------------------------------------------------------------------------------- 1 | fn int main(String[] args) 2 | { 3 | const double[4] ONE = { 1.0, 1.0, 1.0, 1.0 }; 4 | float[<4>] vec4 = ONE; // #error: Implicitly casting 'double[4]' to 'float[<4>]' 5 | } -------------------------------------------------------------------------------- /test/test_suite/visibility/ambiguous_var.c3t: -------------------------------------------------------------------------------- 1 | // #file: file1.c3 2 | module foo; 3 | 4 | int a; 5 | int b; 6 | 7 | // #file: file2.c3 8 | module bar; 9 | int a; 10 | int b; 11 | 12 | // #file: file3.c3 13 | 14 | module baz; 15 | import foo; 16 | import bar; 17 | 18 | int a; 19 | 20 | fn void test2() 21 | @private{ 22 | int c = a; // This is fine. 23 | c = foo::b; 24 | c = bar::b; 25 | c = foo::a; 26 | c = b; // #error: global variable needs a path prefix (e.g. 'foo::b') 27 | } 28 | -------------------------------------------------------------------------------- /test/test_suite/visibility/no_shared_imports.c3t: -------------------------------------------------------------------------------- 1 | // #file: file1.c3 2 | module baz; 3 | 4 | fn void runBar() 5 | { 6 | visible(); 7 | bar::barFunc(); // #error: 'bar::barFunc' could not be found, did you spell it right? 8 | } 9 | 10 | // #file: file2.c3 11 | module baz; 12 | import bar @public; 13 | 14 | fn void visible() @private 15 | { 16 | bar::barFunc(); 17 | } 18 | 19 | // #file: file3.c3 20 | module bar; 21 | 22 | fn void barFunc() @private {} -------------------------------------------------------------------------------- /test/test_suite/visibility/not_visible.c3t: -------------------------------------------------------------------------------- 1 | // #file: file1.c3 2 | module baz; 3 | import bar; 4 | 5 | fn void runBar() 6 | { 7 | bar::notVisible(); // #error: 'bar::notVisible' is '@private' 8 | } 9 | 10 | // #file: file2.c3 11 | module bar; 12 | 13 | fn void notVisible() 14 | @private{ 15 | 16 | } -------------------------------------------------------------------------------- /test/test_suite/visibility/private_import.c3: -------------------------------------------------------------------------------- 1 | module foo; 2 | 3 | fn void hidden() @private 4 | { 5 | } 6 | 7 | module bar; 8 | import foo; 9 | 10 | fn void test() 11 | { 12 | foo::hidden(); // #error: 'foo::hidden' is '@private' 13 | } 14 | 15 | module baz; 16 | import foo @public; 17 | 18 | fn void test() 19 | { 20 | foo::hidden(); 21 | } -------------------------------------------------------------------------------- /test/test_suite/visibility/private_import2.c3: -------------------------------------------------------------------------------- 1 | module test; 2 | 3 | fn void bar() @private 4 | { 5 | } 6 | fn void bar2() @local 7 | { 8 | } 9 | 10 | module baz; 11 | import test @public; 12 | 13 | fn void abc() 14 | { 15 | test::bar(); 16 | test::bar2(); // #error: could not be found 17 | } 18 | 19 | module baz2; 20 | 21 | import test; 22 | 23 | fn void abc() 24 | { 25 | test::bar(); // #error: is '@private' 26 | test::bar2(); // #error: could not be found 27 | } -------------------------------------------------------------------------------- /test/test_suite/visibility/private_to_extern.c3t: -------------------------------------------------------------------------------- 1 | // #target: macos-x64 2 | 3 | module test; 4 | import foo; 5 | 6 | fn int main(String[] args) { 7 | foo::one(); 8 | return 0; 9 | } 10 | 11 | module foo; 12 | 13 | macro one() => two(); 14 | macro two() => three(); 15 | fn void three() @private { four(); } 16 | fn void four() @private {} 17 | 18 | /* #expect: foo.ll 19 | 20 | define void @foo.three() 21 | define internal void @foo.four() -------------------------------------------------------------------------------- /test/test_suite/visibility/shared_module.c3t: -------------------------------------------------------------------------------- 1 | // #file: file1.c3 2 | module baz; 3 | 4 | fn void runBar() 5 | { 6 | visible(); 7 | } 8 | 9 | // #file: file2.c3 10 | module baz; 11 | 12 | fn void visible() @private {} -------------------------------------------------------------------------------- /test/test_suite/visibility/simple_visibility.c3t: -------------------------------------------------------------------------------- 1 | // #file: file1.c3 2 | module baz; 3 | import bar; 4 | 5 | fn void runBar() 6 | { 7 | bar::visible(); 8 | } 9 | 10 | // #file: file2.c3 11 | module bar; 12 | 13 | fn void visible() 14 | { 15 | 16 | } 17 | -------------------------------------------------------------------------------- /test/tmp/.gitkeep: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/tsoding/c3c/3a502feb1db16e1b047d1165baf4635149385182/test/tmp/.gitkeep -------------------------------------------------------------------------------- /test/unit/regression/any.c3: -------------------------------------------------------------------------------- 1 | module any_tests @test; 2 | 3 | fn void any_compare() 4 | { 5 | int x; 6 | any a = &x; 7 | any b = &x; 8 | assert(a == b); 9 | assert(a == a); 10 | } 11 | 12 | def AnyAlias = any; 13 | 14 | fn void test_aliasing() 15 | { 16 | int x; 17 | AnyAlias z = &x; 18 | switch (z) 19 | { 20 | case int: 21 | assert(true); 22 | default: 23 | assert(false); 24 | } 25 | } -------------------------------------------------------------------------------- /test/unit/regression/cast_slice_to_arr.c3: -------------------------------------------------------------------------------- 1 | module slice_to_arr @test; 2 | 3 | fn void to_arr() 4 | { 5 | int[] x = { 1, 2, 3, 4, 5 }; 6 | int z = 2; 7 | int[2] y = x[z:2]; 8 | assert(y == int[2]{ 3, 4 }); 9 | } 10 | 11 | fn void to_vec() 12 | { 13 | int[] x = { 1, 2, 3, 4, 5 }; 14 | int z = 2; 15 | int[<2>] y = x[z:2]; 16 | assert(y == { 3, 4 }); 17 | } -------------------------------------------------------------------------------- /test/unit/regression/catch_err.c3: -------------------------------------------------------------------------------- 1 | module catch_err @test; 2 | 3 | fn void test() 4 | { 5 | anyfault a; 6 | int! z = {| 7 | const ABC = 4; 8 | int! x = SearchResult.MISSING?; 9 | defer (catch err) a = err; 10 | return x; 11 | |}; 12 | assert(a == SearchResult.MISSING); 13 | anyfault y; 14 | z = {| 15 | const ABC = 4; 16 | int! x = 1; 17 | defer (catch err) y = err; 18 | return x; 19 | |}; 20 | assert(!y); 21 | } -------------------------------------------------------------------------------- /test/unit/regression/copysign.c3: -------------------------------------------------------------------------------- 1 | module copysign @test; 2 | import std::math; 3 | fn void copysign_float() 4 | { 5 | float a = 3; 6 | float b = -4; 7 | float c = math::copysign(a, b); 8 | assert(c == -3); 9 | float d = math::copysign(a, 3); 10 | assert(d == 3); 11 | assert(math::copysign(a, -3) == -3); 12 | float e = math::copysign(3, a); 13 | assert(e == 3); 14 | assert(math::copysign(3, b) == -3); 15 | } -------------------------------------------------------------------------------- /test/unit/regression/faults.c3: -------------------------------------------------------------------------------- 1 | module faults @test; 2 | 3 | fault Foo 4 | { 5 | ABC, 6 | CDE 7 | } 8 | 9 | fn void ordinals() 10 | { 11 | Foo z = {}; 12 | assert(z.ordinal == 0); 13 | $assert Foo.ABC.ordinal == 1; 14 | $assert Foo.CDE.ordinal == 2; 15 | $assert (Foo{}).ordinal == 0; 16 | Foo x = Foo.CDE; 17 | assert(x.ordinal == 2); 18 | x = Foo.ABC; 19 | assert(x.ordinal == 1); 20 | } 21 | 22 | -------------------------------------------------------------------------------- /test/unit/regression/int128.c3: -------------------------------------------------------------------------------- 1 | module int128_test; 2 | 3 | fn void check(uint128 a, uint128 b) 4 | { 5 | uint128 div = a / b; 6 | uint128 mod = a % b; 7 | assert(div * b + mod == a); 8 | } 9 | 10 | fn void test_big() @test 11 | { 12 | uint128 a = 12345678901234567890012u128; 13 | uint128 b = 1234567890123456789001u128; 14 | for (int i = 0; i < 10; i++) 15 | { 16 | for (int j = 0; j < 10; j++) 17 | { 18 | check(a + i, b + j); 19 | } 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /test/unit/regression/int_min.c3: -------------------------------------------------------------------------------- 1 | fn void int_min() @test 2 | { 3 | assert(int.min == -2147483648); 4 | assert((float)int.min == -2147483648.0f); 5 | assert(short.min == -32768); 6 | assert((float)short.min == -32768.0f); 7 | assert(ichar.min == -128); 8 | assert((float)ichar.min == -128.0f); 9 | } 10 | -------------------------------------------------------------------------------- /test/unit/regression/liveness_any.c3: -------------------------------------------------------------------------------- 1 | module liveness; 2 | 3 | interface TestProto 4 | { 5 | fn void tesT(); 6 | } 7 | 8 | fn void Test.tesT(&self) @dynamic 9 | {} 10 | 11 | struct Test (TestProto) 12 | { 13 | void* abc; 14 | } 15 | 16 | fn void reflect_test() @test 17 | { 18 | TestProto b = mem::alloc(Test); 19 | b.tesT(); 20 | } -------------------------------------------------------------------------------- /test/unit/regression/lvalue_handling.c3: -------------------------------------------------------------------------------- 1 | module lvalue_handling; 2 | import std; 3 | struct Foo 4 | { 5 | int a; 6 | } 7 | def IntList = List(); 8 | fn void subscript_overload() @test 9 | { 10 | IntList x; 11 | x.push({ 3 }); 12 | int* a = &x[0].a; 13 | assert(*a == 3); 14 | assert(x[0].a == 3); 15 | *a = 4; 16 | assert(x[0].a == 4); 17 | x[0].a = 5; 18 | assert(x[0].a == 5); 19 | } -------------------------------------------------------------------------------- /test/unit/regression/pointer_diff.c3: -------------------------------------------------------------------------------- 1 | import std; 2 | struct Foo 3 | { 4 | int a,b,c,d; 5 | } 6 | 7 | fn void pointer_diff() @test 8 | { 9 | Foo* foo; 10 | isz offset = &foo[1] - &foo[0]; 11 | assert(offset == 1); 12 | } 13 | 14 | fn void pointer_add() @test 15 | { 16 | Foo* foo; 17 | Foo* bar = foo + 2; 18 | isz offset = bar - foo; 19 | assert(offset == 2); 20 | } -------------------------------------------------------------------------------- /test/unit/regression/pointer_non_decay.c3: -------------------------------------------------------------------------------- 1 | module test @test; 2 | 3 | fn void pointer_non_decay() 4 | { 5 | int[3] x; 6 | int[3]* y = &x; 7 | int* z = y; 8 | int[] sub = y; 9 | int[3] y1 = y[1]; 10 | int z1 = z[1]; 11 | int* xx = &x + 1; 12 | int[3]* yy = (int[3]*)(xx); 13 | int* zz = yy - 1; 14 | assert(y == z); 15 | assert(z == zz); 16 | assert(&(*y)[1] == &xx[-2]); 17 | x[1] = 123; 18 | assert(x[1] == z[1]); 19 | } -------------------------------------------------------------------------------- /test/unit/regression/select.c3: -------------------------------------------------------------------------------- 1 | import std; 2 | fn long[<4>] process(long[<4>] a, long[<4>] b) @noinline 3 | { 4 | return math::select({ true, true, false, true }, a, b); 5 | } 6 | fn void test_select() @test 7 | { 8 | long[<4>] res = process({ 4, 5, 6, 7 }, { 100, 200, 300, 400 }); 9 | assert(res == { 4, 5, 300, 7}); 10 | } 11 | -------------------------------------------------------------------------------- /test/unit/regression/slice_assign.c3: -------------------------------------------------------------------------------- 1 | module slice_assign @test; 2 | 3 | fn void assign_slice() 4 | { 5 | int[8] a; 6 | a[2..3] = { 1, 2 }; 7 | a[5..7] = 5; 8 | assert(a == int[8]{ 0, 0, 1, 2, 0, 5, 5, 5}); 9 | } -------------------------------------------------------------------------------- /test/unit/regression/struct_alignment.c3: -------------------------------------------------------------------------------- 1 | module struct_alignment @test; 2 | 3 | struct Test @align(16) { void* foo; } 4 | 5 | struct Test2 6 | { 7 | Test test; 8 | uint a; 9 | } 10 | 11 | fn void nested_struct() 12 | { 13 | Test2* array; 14 | assert((uptr)&array[1] - (uptr)array == 32); 15 | assert((uptr)&array[1] - (uptr)array == Test2.sizeof); 16 | assert(Test2.sizeof == 32); 17 | assert(Test.sizeof == 16); 18 | } -------------------------------------------------------------------------------- /test/unit/regression/subscripting.c3: -------------------------------------------------------------------------------- 1 | module subscripting_tests @test; 2 | 3 | fn void subscript_ct() 4 | { 5 | $if int.nameof[0] == 'i': 6 | assert(true); 7 | $else 8 | assert(false); 9 | $endif 10 | $if int.nameof[^1] == 't': 11 | assert(true); 12 | $else 13 | assert(false); 14 | $endif 15 | } -------------------------------------------------------------------------------- /test/unit/regression/ternary.c3: -------------------------------------------------------------------------------- 1 | module test @test; 2 | 3 | fn void const_ternary() 4 | { 5 | int foo = 1; 6 | const int FOO = 1; 7 | assert((foo ?: 2) == 1); 8 | assert((FOO ?: 2) == 1); 9 | int bar = 2; 10 | assert((FOO ?: bar) == 1); 11 | } 12 | -------------------------------------------------------------------------------- /test/unit/regression/unwrapping.c3: -------------------------------------------------------------------------------- 1 | module unwrapping; 2 | 3 | fn bool! get_bool() 4 | { 5 | return true; 6 | } 7 | 8 | fn void bool_chain_unwrap() @test 9 | { 10 | bool b; 11 | if (try v = get_bool() && b) 12 | { 13 | assert(v == true); 14 | } 15 | if (try v = get_bool() && v) 16 | { 17 | assert(v == true); 18 | } 19 | } -------------------------------------------------------------------------------- /test/unit/regression/vector_method_reduce.c3: -------------------------------------------------------------------------------- 1 | import std::math; 2 | 3 | fn void vector_method_reduce() @test 4 | { 5 | float[<3>] x = { 1, 2.0, 4.0 }; 6 | int[] y = { -23, 1, 4 }; 7 | assert(y.sum() == -18); 8 | assert(y.product() == -92); 9 | assert(y.max() == 4); 10 | assert(y.and() == 0); 11 | assert(y.xor() == -20); 12 | assert(y.min() == -23); 13 | assert(y.or() == -19); 14 | assert(x.sum(1.2) - 8.2 < 0.000001); 15 | assert(x.product(1.2) - 9.6 < 0.000001); 16 | assert(x.min() == 1.0); 17 | assert(x.max() == 4.0); 18 | } -------------------------------------------------------------------------------- /test/unit/stdlib/collections/generic_list.c3: -------------------------------------------------------------------------------- 1 | module glist @test; 2 | import std::collections; 3 | 4 | fn void simple_use() 5 | { 6 | AnyList l; 7 | l.push(1); 8 | l.push("Hello"); 9 | assert(l.get(1, String)!! == "Hello"); 10 | assert(l.get(0, int)!! == 1); 11 | assert(l.pop(String)!! == "Hello"); 12 | assert(l.pop(int)!! == 1); 13 | assert(l.len() == 0); 14 | l.free(); 15 | } -------------------------------------------------------------------------------- /test/unit/stdlib/core/formatter.c3: -------------------------------------------------------------------------------- 1 | module std::core::formatter_test; 2 | 3 | import std; 4 | 5 | struct Foo (Printable) { int a; } 6 | fn usz! Foo.to_format(&self, Formatter *f) @dynamic 7 | { 8 | return f.printf("Foo[%d]", self.a); 9 | } 10 | 11 | fn void test_ref() @test 12 | { 13 | Foo* f = &&Foo{ 8 }; 14 | Foo* f0 = null; 15 | int* a = (void*)(uptr)0x40; 16 | int* b = null; 17 | String s = string::new_format("%s %s %s %s %s", a, b, f0, f, *f); 18 | defer free(s); 19 | assert(s == "0x40 0x0 (null) Foo[8] Foo[8]"); 20 | } 21 | -------------------------------------------------------------------------------- /test/unit/stdlib/crypto/rc4.c3: -------------------------------------------------------------------------------- 1 | import std::crypto; 2 | import std::io; 3 | 4 | fn void rc_crypt() @test 5 | { 6 | Rc4 rc; 7 | rc.init(&&x"63727970746969"); 8 | char[200] x; 9 | String text = "The quick brown fox jumps over the lazy dog."; 10 | rc.crypt(text, &x); 11 | char[?] res = x'2ac2fecdd8fbb84638e3a4 12 | 820eb205cc8e29c28b9d5d 13 | 6b2ef974f311964971c90e 14 | 8b9ca16467ef2dc6fc3520'; 15 | assert(res[:text.len] == x[:text.len]); 16 | } -------------------------------------------------------------------------------- /test/unit/stdlib/io/dstringstream.c3: -------------------------------------------------------------------------------- 1 | module std::io @test; 2 | 3 | fn void test_writing() 4 | { 5 | DString foo; 6 | foo.new_init(); 7 | OutStream s = &foo; 8 | s.write("hello")!!; 9 | s.write_byte('-')!!; 10 | s.write("what?-------------------------------------------------------")!!; 11 | ByteReader r; 12 | String test_str = "2134"; 13 | io::copy_to(r.init(test_str), s)!!; 14 | String o = foo.str_view(); 15 | assert(o == "hello-what?-------------------------------------------------------2134"); 16 | } 17 | -------------------------------------------------------------------------------- /test/unit/stdlib/io/fileinfo.c3: -------------------------------------------------------------------------------- 1 | module std::io::fileinfo @test; 2 | import std::io::os; 3 | 4 | fn void test_native_is_file() @if(env::LINUX || env::DARWIN) 5 | { 6 | assert(!os::native_is_file("/dev/loop0")); 7 | assert(!os::native_is_file("/dev/null")); 8 | } 9 | 10 | fn void test_native_is_dir() @if(env::LINUX || env::DARWIN) 11 | { 12 | assert(os::native_is_dir("/")); 13 | assert(!os::native_is_file("/")); 14 | assert(!os::native_is_dir("/dev/loop0")); 15 | assert(!os::native_is_dir("/dev/null")); 16 | } -------------------------------------------------------------------------------- /test/unit/stdlib/io/limitreader.c3: -------------------------------------------------------------------------------- 1 | module std::io @test; 2 | 3 | 4 | fn void limitreader() 5 | { 6 | const DATA = "Hello World!"; 7 | ByteReader src; 8 | src.init(DATA); 9 | const LIMIT = 5; 10 | LimitReader lmr; 11 | lmr.init(&src, LIMIT); 12 | 13 | char[DATA.len] bytes; 14 | usz n = lmr.read(bytes[..])!!; 15 | 16 | assert(n == LIMIT, "got %d; want %d", n, LIMIT); 17 | String got = (String)bytes[:n]; 18 | String want = DATA[:LIMIT]; 19 | assert(got == want, "got %d; want %d", got, want); 20 | } -------------------------------------------------------------------------------- /test/unit/stdlib/io/multireader.c3: -------------------------------------------------------------------------------- 1 | module std::io @test; 2 | 3 | fn void test_multireader() 4 | { 5 | MultiReader mr; 6 | mr.temp_init( 7 | &&wrap_bytes("foo"), 8 | &&wrap_bytes(" "), 9 | &&wrap_bytes("bar"), 10 | &&wrap_bytes("!"), 11 | ); 12 | defer mr.free(); 13 | 14 | ByteWriter w; 15 | io::copy_to(&mr, w.temp_init())!!; 16 | 17 | String want = "foo bar!"; 18 | assert(w.str_view() == want, 19 | "invalid data read; got: %s, want: %s", w.str_view(), want); 20 | } 21 | 22 | -------------------------------------------------------------------------------- /test/unit/stdlib/io/multiwriter.c3: -------------------------------------------------------------------------------- 1 | module std::io @test; 2 | 3 | fn void test_multiwriter() 4 | { 5 | ByteWriter w1, w2; 6 | MultiWriter mw; 7 | mw.temp_init(w1.temp_init(), w2.temp_init()); 8 | defer mw.free(); 9 | 10 | String want = "foobar"; 11 | io::copy_to(ByteReader{}.init(want), &mw)!!; 12 | 13 | assert(w1.str_view() == want, 14 | "invalid write; got: %s, want: %s", w1.str_view(), want); 15 | assert(w2.str_view() == want, 16 | "invalid write; got: %s, want: %s", w2.str_view(), want); 17 | } 18 | -------------------------------------------------------------------------------- /test/unit/stdlib/io/teereader.c3: -------------------------------------------------------------------------------- 1 | module std::io @test; 2 | 3 | fn void test_teereader() 4 | { 5 | String want = "foobar"; 6 | 7 | ByteWriter w; 8 | TeeReader r = tee_reader(ByteReader{}.init(want), w.temp_init()); 9 | 10 | char[16] buf; 11 | usz n = r.read(buf[..])!!; 12 | 13 | String got = w.str_view(); 14 | assert(n == want.len, "teereader: invalid length"); 15 | assert(got == want, "teereader: got: %s, want: %s", got, want); 16 | assert(got == (String)buf[:n], "teereader: got: %s, want: %s", got, (String)buf[:n]); 17 | } 18 | -------------------------------------------------------------------------------- /test/unit/stdlib/macros/core_builtins.c3: -------------------------------------------------------------------------------- 1 | module core_builtin_tests; 2 | 3 | fn void test_likely() @test 4 | { 5 | assert(@likely(2 > 1)); 6 | assert(@likely(2 > 1, 0.5)); 7 | } 8 | 9 | fn void test_unlikely() @test 10 | { 11 | assert(!@unlikely(2 < 1)); 12 | assert(!@unlikely(2 < 1, 0.5)); 13 | } 14 | 15 | fn void test_expect() @test 16 | { 17 | assert(@expect(2 > 1, true)); 18 | assert(!@expect(2 < 1, false)); 19 | 20 | assert(@expect(2 > 1, true, 0.5)); 21 | assert(!@expect(2 < 1, false, 0.5)); 22 | } 23 | 24 | -------------------------------------------------------------------------------- /test/unit/stdlib/math/frexp_signbit.c3: -------------------------------------------------------------------------------- 1 | module std::math @test; 2 | 3 | fn void test_frexp() 4 | { 5 | int a; 6 | double z = math::frexp(231.23, &a); 7 | assert((z - 0.903242187) < 0.0000001 && a == 8); 8 | float z2 = math::frexp(231.23f, &a); 9 | assert((z2 - 0.903242187) < 0.0000001 && a == 8); 10 | } 11 | 12 | fn void test_signbit() 13 | { 14 | assert(math::signbit(-231.3) == 1); 15 | assert(math::signbit(231.3) == 0); 16 | assert(math::signbit(float.inf) == 0); 17 | assert(math::signbit(-float.inf) == 1); 18 | } 19 | -------------------------------------------------------------------------------- /test/unit/stdlib/os/env.c3: -------------------------------------------------------------------------------- 1 | module std::os::env @test; 2 | 3 | fn void set_get_unset() 4 | { 5 | const NAME = "C3_TEST_ENVVAR"; 6 | const VALUE = "foobar"; 7 | 8 | env::set_var(NAME, VALUE); 9 | String v = env::get_var(NAME)!!; 10 | assert(v == VALUE, "got %s; want %s", v, VALUE); 11 | 12 | env::clear_var(NAME); 13 | if (try env::get_var(NAME)) 14 | { 15 | unreachable("environment variable should no longer exist"); 16 | } 17 | } -------------------------------------------------------------------------------- /test/unit/stdlib/sort/sort.c3: -------------------------------------------------------------------------------- 1 | module std::sort; 2 | 3 | fn int cmp_int_ref(int* x, int* y) 4 | { 5 | return *x - *y; 6 | } 7 | 8 | fn int cmp_int_value(int x, int y) 9 | { 10 | return x - y; 11 | } 12 | 13 | 14 | fn uint key_int_ref(int* x) 15 | { 16 | return (uint)(*x + int.min); 17 | } 18 | 19 | fn uint key_int_value(int x) 20 | { 21 | return (uint)(x + int.min); 22 | } -------------------------------------------------------------------------------- /test/unit/stdlib/string.c3: -------------------------------------------------------------------------------- 1 | module string_test; 2 | 3 | fn void test_clear() @test 4 | { 5 | DString s = dstring::new_with_capacity(32); 6 | assert(s.len() == 0); 7 | assert(s.capacity() == 32); 8 | s.append_repeat('x', 63); 9 | assert(s.capacity() == 64); 10 | assert(s.len() == 63); 11 | char* addr = (char*)s.str_view(); 12 | s.clear(); 13 | assert(s.capacity() == 64); 14 | assert(s.len() == 0); 15 | s.append_repeat('x', 63); 16 | assert(s.capacity() == 64); 17 | assert(s.len() == 63); 18 | assert(addr == (char*)s.str_view()); 19 | } --------------------------------------------------------------------------------