Minor refactorings. Added "Thank you" section to readme. Some fixes to hostinfo.

This commit is contained in:
Christoffer Lerno
2024-09-12 13:47:49 +02:00
parent d376ee6671
commit 65c48419d0
8 changed files with 69 additions and 69 deletions

View File

@@ -374,11 +374,9 @@ if(C3_WITH_LLVM)
src/compiler/llvm_codegen_builtins.c)
target_compile_definitions(c3c PUBLIC LLVM_AVAILABLE=1)
add_library(c3c_wrappers STATIC wrapper/src/wrapper.cpp)
else()
target_sources(c3c PRIVATE src/utils/hostinfo.c)
target_compile_definitions(c3c PUBLIC LLVM_AVAILABLE=0)
endif()

View File

@@ -369,3 +369,9 @@ Editor plugins can be found at https://github.com/c3lang/editor-plugins.
3. Run tests and see that they pass. (Recommended settings: `c3c compile-test -O0 test/unit`.
- in this example `test/unit/` is the relative path to the test directory, so adjust as required)
4. Make a pull request for the new tests.
## Thank yous
A huge "thank you" goes out to all contributors and sponsors.
A special thank you to sponsor @Caleb-o for going the extra mile.

View File

@@ -168,6 +168,7 @@ bool type_homogenous_aggregate_small_enough(Type *type, unsigned members)
*/
bool type_is_homogenous_aggregate(Type *type, Type **base, unsigned *elements)
{
assert(base && type && elements);
assert(type_lowering(type) == type);
*elements = 0;
switch (type->type_kind)

View File

@@ -2161,7 +2161,7 @@ bool expr_is_pure(Expr *expr);
bool expr_is_constant_eval(Expr *expr, ConstantEvalKind eval_kind);
bool expr_is_compile_time(Expr *ast, ConstantEvalKind eval_kind);
bool range_is_const(Range *range);
Expr *expr_generate_decl(Decl *decl, Expr *assign);
void expr_insert_addr(Expr *original);
void expr_rewrite_insert_deref(Expr *original);

View File

@@ -256,7 +256,7 @@ Expr *sema_enter_inline_member(Expr *parent, CanonicalType *type)
}
}
Expr *sema_expr_analyse_ct_arg_index(SemaContext *context, Expr *index_expr, unsigned *index_ref, bool report_error)
Expr *sema_expr_analyse_ct_arg_index(SemaContext *context, Expr *index_expr, unsigned *index_ref)
{
unsigned args = vec_size(context->macro_varargs);
uint64_t index;
@@ -264,24 +264,24 @@ Expr *sema_expr_analyse_ct_arg_index(SemaContext *context, Expr *index_expr, uns
if (!sema_analyse_expr(context, index_expr)) return poisoned_expr;
if (!type_is_integer(index_expr->type))
{
if (report_error) SEMA_ERROR(index_expr, "Expected the argument index here, but found a value of type %s.", type_quoted_error_string(index_expr->type));
SEMA_ERROR(index_expr, "Expected the argument index here, but found a value of type %s.", type_quoted_error_string(index_expr->type));
return poisoned_expr;
}
if (!sema_cast_const(index_expr))
{
if (report_error) SEMA_ERROR(index_expr, "Vararg functions need a constant argument, but this is a runtime value.");
SEMA_ERROR(index_expr, "Vararg functions need a constant argument, but this is a runtime value.");
return poisoned_expr;
}
Int index_val = index_expr->const_expr.ixx;
if (int_is_neg(index_val))
{
if (report_error) SEMA_ERROR(index_expr, "The index cannot be negative.");
SEMA_ERROR(index_expr, "The index cannot be negative.");
return poisoned_expr;
}
Int int_max = { .i = { .low = args }, .type = TYPE_U32 };
if (int_comp(index_val, int_max, BINARYOP_GE))
{
if (report_error) SEMA_ERROR(index_expr, "Only %u vararg%s exist.", args, args == 1 ? "" : "s");
SEMA_ERROR(index_expr, "Only %u vararg%s exist.", args, args == 1 ? "" : "s");
return poisoned_expr;
}
if (index_ref) *index_ref = (unsigned)index_val.i.low;
@@ -4877,6 +4877,7 @@ CHECK_DEEPER:
}
if (ambiguous)
{
assert(member);
RETURN_SEMA_ERROR(expr, "'%s' is an ambiguous name and so cannot be resolved, it may refer to method defined in '%s' or one in '%s'",
kw, member->unit->module->name->module, ambiguous->unit->module->name->module);
}
@@ -5143,15 +5144,6 @@ static inline bool sema_expr_analyse_cast(SemaContext *context, Expr *expr, bool
return true;
}
bool range_is_const(Range *range)
{
Expr *start = exprptr(range->start);
Expr *end = exprptrzero(range->end);
if (end && !expr_is_const(end)) return false;
if (start && !expr_is_const(start)) return false;
return true;
}
static bool sema_expr_analyse_slice_assign(SemaContext *context, Expr *expr, Type *left_type, Expr *right, bool is_unwrapped)
{
Expr *left = exprptr(expr->binary_expr.left);
@@ -7973,8 +7965,8 @@ RETRY:
case TYPE_INFO_VATYPE:
{
if (!context->current_macro) return NULL;
Expr *arg_expr = sema_expr_analyse_ct_arg_index(context, type_info->unresolved_type_expr, NULL, false);
if (!expr_ok(arg_expr)) return NULL;
Expr *arg_expr = sema_expr_analyse_ct_arg_index(context, type_info->unresolved_type_expr, NULL);
if (!expr_ok(arg_expr)) return poisoned_type;
if (!sema_analyse_expr_value(context, arg_expr)) return poisoned_type;
if (arg_expr->expr_kind != EXPR_TYPEINFO) return NULL;
return arg_expr->type_expr->type->canonical;
@@ -8311,7 +8303,7 @@ static inline bool sema_expr_analyse_lambda(SemaContext *context, Type *target_t
decl->extname = decl->name;
decl->type = type_new_func(decl, sig);
if (!sema_analyse_function_signature(context, decl, sig->abi, sig)) return false;
if (target_type && flat->pointer->function.prototype->raw_type != decl->type->function.prototype->raw_type)
if (flat && flat->pointer->function.prototype->raw_type != decl->type->function.prototype->raw_type)
{
RETURN_SEMA_ERROR(expr, "The lambda has type %s, which doesn't match the required type %s.",
type_quoted_error_string(decl->type),
@@ -8594,8 +8586,7 @@ static inline bool sema_expr_analyse_ct_arg(SemaContext *context, Type *infer_ty
{
unsigned index = 0;
// A normal argument, this means we only evaluate it once.
ASSIGN_EXPR_OR_RET(Expr *arg_expr, sema_expr_analyse_ct_arg_index(context, exprptr(expr->ct_arg_expr.arg),
&index, true), false);
ASSIGN_EXPR_OR_RET(Expr *arg_expr, sema_expr_analyse_ct_arg_index(context, exprptr(expr->ct_arg_expr.arg), &index), false);
index++;
ASSERT_SPAN(expr, index < 0x10000);
@@ -8632,22 +8623,19 @@ static inline bool sema_expr_analyse_ct_arg(SemaContext *context, Type *infer_ty
case TOKEN_CT_VAEXPR:
{
// An expr argument, this means we copy and evaluate.
ASSIGN_EXPR_OR_RET(Expr *arg_expr, sema_expr_analyse_ct_arg_index(context, exprptr(expr->ct_arg_expr.arg),
NULL, true), false);
ASSIGN_EXPR_OR_RET(Expr *arg_expr, sema_expr_analyse_ct_arg_index(context, exprptr(expr->ct_arg_expr.arg), NULL), false);
expr_replace(expr, copy_expr_single(arg_expr));
return sema_analyse_inferred_expr(context, infer_type, expr);
}
case TOKEN_CT_VACONST:
{
// An expr argument, this means we copy and evaluate.
ASSIGN_EXPR_OR_RET(Expr *arg_expr, sema_expr_analyse_ct_arg_index(context, exprptr(expr->ct_arg_expr.arg),
NULL, true), false);
ASSIGN_EXPR_OR_RET(Expr *arg_expr, sema_expr_analyse_ct_arg_index(context, exprptr(expr->ct_arg_expr.arg), NULL), false);
arg_expr = copy_expr_single(arg_expr);
if (!sema_analyse_inferred_expr(context, infer_type, arg_expr)) return false;
if (!expr_is_constant_eval(arg_expr, CONSTANT_EVAL_CONSTANT_VALUE))
{
SEMA_ERROR(arg_expr, "This argument needs to be a compile time constant.");
return false;
RETURN_SEMA_ERROR(arg_expr, "This argument needs to be a compile time constant.");
}
expr_replace(expr, arg_expr);
return true;
@@ -8655,10 +8643,8 @@ static inline bool sema_expr_analyse_ct_arg(SemaContext *context, Type *infer_ty
case TOKEN_CT_VAREF:
{
// A normal argument, this means we only evaluate it once.
unsigned index;
ASSIGN_EXPR_OR_RET(Expr *arg_expr, sema_expr_analyse_ct_arg_index(context, exprptr(expr->ct_arg_expr.arg),
&index, true), false);
unsigned index = 0;
ASSIGN_EXPR_OR_RET(Expr *arg_expr, sema_expr_analyse_ct_arg_index(context, exprptr(expr->ct_arg_expr.arg), &index), false);
index++;
ASSERT_SPAN(expr, index < 0x10000);

View File

@@ -99,7 +99,7 @@ bool sema_expr_analyse_builtin_call(SemaContext *context, Expr *expr);
bool sema_expr_analyse_macro_call(SemaContext *context, Expr *call_expr, Expr *struct_var, Decl *decl, bool optional,
bool *no_match_ref);
Expr *sema_expr_analyse_ct_arg_index(SemaContext *context, Expr *index_expr, unsigned *index_ref, bool report_error);
Expr *sema_expr_analyse_ct_arg_index(SemaContext *context, Expr *index_expr, unsigned *index_ref);
Expr *sema_ct_eval_expr(SemaContext *context, bool is_type, Expr *inner, bool report_missing);
bool sema_analyse_asm(SemaContext *context, AsmInlineBlock *block, Ast *asm_stmt);

View File

@@ -340,8 +340,7 @@ INLINE bool sema_resolve_vatype(SemaContext *context, TypeInfo *type_info)
{
RETURN_SEMA_ERROR(type_info, "'%s' can only be used inside of a macro.", token_type_to_string(TOKEN_CT_VATYPE));
}
ASSIGN_EXPR_OR_RET(Expr *arg_expr, sema_expr_analyse_ct_arg_index(context, type_info->unresolved_type_expr, NULL,
true), false);
ASSIGN_EXPR_OR_RET(Expr *arg_expr, sema_expr_analyse_ct_arg_index(context, type_info->unresolved_type_expr, NULL), false);
if (!sema_analyse_expr_value(context, arg_expr)) return false;
if (arg_expr->expr_kind != EXPR_TYPEINFO) RETURN_SEMA_ERROR(arg_expr, "The argument was not a type.");
type_info->type = arg_expr->type_expr->type;
@@ -600,9 +599,9 @@ static inline Type *func_create_new_func_proto(Signature *sig, CallABI abi, uint
scratch_buffer_append("fn ");
type_append_name_to_scratch(proto->rtype);
scratch_buffer_append_char('(');
FOREACH_IDX(index, Type *, val, proto->param_types)
FOREACH_IDX(idx, Type *, val, proto->param_types)
{
if (index != 0) scratch_buffer_append(", ");
if (idx != 0) scratch_buffer_append(", ");
type_append_name_to_scratch(val);
}
scratch_buffer_append_char(')');

View File

@@ -3,14 +3,16 @@
#include "hostinfo.h"
#include <stdlib.h>
static int is_le(void) {
static int is_le(void)
{
unsigned int i = 1;
char *c;
c = (char *) &i;
return (*c == 1);
}
ArchType hostinfo_arch_type(void) {
ArchType hostinfo_arch_type(void)
{
#if defined(__x86_64__) || defined(_M_X64)
return ARCH_TYPE_X86_64;
#elif defined(i386) || defined(__i386__) || defined(__i386) || defined(_M_IX86)
@@ -36,12 +38,14 @@ ArchType hostinfo_arch_type(void) {
#elif defined(__sparc__) || defined(__sparc)
return ARCH_UNSUPPORTED
#else
return ARCH_UNSUPPORTED
return ARCH_TYPE_UNKNOWN;
#endif
}
static const char * llvm_arch_name(ArchType ty) {
switch (ty) {
static const char *llvm_arch_name(ArchType ty)
{
switch (ty)
{
case ARCH_TYPE_X86_64: return "x86_64";
case ARCH_TYPE_X86: return "x86";
case ARCH_TYPE_ARM: return "arm";
@@ -58,55 +62,60 @@ static const char * llvm_arch_name(ArchType ty) {
case ARCH_TYPE_PPC64LE: return "ppc64le";
case ARCH_TYPE_RISCV32: return "riscv32";
case ARCH_TYPE_RISCV64: return "riscv64";
default:
case ARCH_UNSUPPORTED:
case ARCH_TYPE_UNKNOWN: return "unknown";
}
UNREACHABLE
}
void hostinfo_x86_features(X86Features *cpu_features) {
void hostinfo_x86_features(X86Features *cpu_features)
{
#if defined(__x86_64__) || defined(_M_X64)
// TODO
#endif
}
EnvironmentType hostinfo_env_type(void) {
EnvironmentType hostinfo_env_type(void)
{
return ENV_TYPE_UNKNOWN;
}
OsType hostinfo_os_type(void) {
if (system("freebsd-version -k") == 0) {
return OS_TYPE_FREE_BSD;
}
if (system("uname -r") == 0) {
return OS_TYPE_LINUX;
}
if (system("cd C:/Windows") == 0) {
return OS_TYPE_WIN32;
}
OsType hostinfo_os_type(void)
{
#if __APPLE__
return OS_TYPE_MACOSX;
#else
if (system("freebsd-version -k") == 0) return OS_TYPE_FREE_BSD;
if (system("uname -r") == 0) return OS_TYPE_LINUX;
if (system("cd C:/Windows") == 0) return OS_TYPE_WIN32;
return OS_TYPE_UNKNOWN;
#endif
}
static const char * llvm_os_name(OsType os) {
switch (os) {
case OS_TYPE_FREE_BSD: return "frebsd";
case OS_TYPE_LINUX: return "linux";
case OS_TYPE_WIN32: return "win32";
default: return "unknown";
}
static const char *llvm_os_name(OsType os)
{
switch (os)
{
case OS_TYPE_FREE_BSD: return "freebsd";
case OS_TYPE_LINUX: return "linux";
case OS_TYPE_WIN32: return "win32";
case OS_TYPE_MACOSX: return "darwin";
default: return "unknown";
}
}
VendorType hostinfo_vendor_type(void) {
VendorType hostinfo_vendor_type(void)
{
return VENDOR_UNKNOWN;
}
static char triple[128];
static int triple_init = 0;
const char * hostinfo_default_triple(void) {
if (!triple_init) {
const char * hostinfo_default_triple(void)
{
if (!triple_init)
{
sprintf(triple, "%s-unknown-unknown-%s",
llvm_arch_name(hostinfo_arch_type()),
llvm_os_name(hostinfo_os_type()));
@@ -116,6 +125,7 @@ const char * hostinfo_default_triple(void) {
return triple;
}
const char * hostinfo_x86_cpu_name(void) {
const char *hostinfo_x86_cpu_name(void)
{
return "x86";
}