Skip to content

Add decoding to section mangler #1205

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 8 commits into from
Jun 13, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
The table of contents is too big for display.
Diff view
Diff view
  •  
  •  
  •  
3 changes: 3 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ expression: "results.join(\"\\n\")"
; ModuleID = 'main.st'
source_filename = "main.st"

define i16 @main() section "fn-main:i16" {
define i16 @main() section "fn-$RUSTY$main:i16" {
entry:
%main = alloca i16, align 2
store i16 0, i16* %main, align 2
Expand All @@ -14,9 +14,9 @@ entry:
ret i16 %main_ret
}

declare i16 @external() section "fn-external:i16"
declare i16 @external() section "fn-$RUSTY$external:i16"

; ModuleID = 'external.st'
source_filename = "external.st"

declare i16 @external() section "fn-external:i16"
declare i16 @external() section "fn-$RUSTY$external:i16"
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,10 @@ expression: "results.join(\"\\n\")"
; ModuleID = 'main.st'
source_filename = "main.st"

@x = external global i16, section "var-x:i16"
@y = external global i16, section "var-y:i16"
@x = external global i16, section "var-$RUSTY$x:i16"
@y = external global i16, section "var-$RUSTY$y:i16"

define i16 @main() section "fn-main:i16" {
define i16 @main() section "fn-$RUSTY$main:i16" {
entry:
%main = alloca i16, align 2
store i16 0, i16* %main, align 2
Expand All @@ -19,12 +19,12 @@ entry:
ret i16 %main_ret
}

declare i16 @external() section "fn-external:i16"
declare i16 @external() section "fn-$RUSTY$external:i16"

; ModuleID = 'external.st'
source_filename = "external.st"

@x = external global i16, section "var-x:i16"
@y = external global i16, section "var-y:i16"
@x = external global i16, section "var-$RUSTY$x:i16"
@y = external global i16, section "var-$RUSTY$y:i16"

declare i16 @external() section "fn-external:i16"
declare i16 @external() section "fn-$RUSTY$external:i16"
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,9 @@ source_filename = "app/file1.st"

%mainProg = type {}

@mainProg_instance = external global %mainProg, section "var-mainProg_instance:r0", !dbg !0
@mainProg_instance = external global %mainProg, section "var-$RUSTY$mainProg_instance:r0", !dbg !0

define i16 @main() section "fn-main:i16" !dbg !10 {
define i16 @main() section "fn-$RUSTY$main:i16" !dbg !10 {
entry:
%main = alloca i16, align 2, !dbg !14
call void @llvm.dbg.declare(metadata i16* %main, metadata !15, metadata !DIExpression()), !dbg !17
Expand All @@ -19,7 +19,7 @@ entry:
ret i16 %main_ret, !dbg !14
}

declare !dbg !18 void @mainProg(%mainProg*) section "fn-mainProg:v"
declare !dbg !18 void @mainProg(%mainProg*) section "fn-$RUSTY$mainProg:v"

; Function Attrs: nofree nosync nounwind readnone speculatable willreturn
declare void @llvm.dbg.declare(metadata, metadata, metadata) #0
Expand Down Expand Up @@ -54,9 +54,9 @@ source_filename = "lib/file2.st"

%mainProg = type {}

@mainProg_instance = global %mainProg zeroinitializer, section "var-mainProg_instance:r0", !dbg !0
@mainProg_instance = global %mainProg zeroinitializer, section "var-$RUSTY$mainProg_instance:r0", !dbg !0

define void @mainProg(%mainProg* %0) section "fn-mainProg:v" !dbg !10 {
define void @mainProg(%mainProg* %0) section "fn-$RUSTY$mainProg:v" !dbg !10 {
entry:
call void @llvm.dbg.declare(metadata %mainProg* %0, metadata !13, metadata !DIExpression()), !dbg !14
ret void, !dbg !14
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,9 @@ source_filename = "file1.st"

%mainProg = type {}

@mainProg_instance = external global %mainProg, section "var-mainProg_instance:r0", !dbg !0
@mainProg_instance = external global %mainProg, section "var-$RUSTY$mainProg_instance:r0", !dbg !0

define i16 @main() section "fn-main:i16" !dbg !10 {
define i16 @main() section "fn-$RUSTY$main:i16" !dbg !10 {
entry:
%main = alloca i16, align 2, !dbg !14
call void @llvm.dbg.declare(metadata i16* %main, metadata !15, metadata !DIExpression()), !dbg !17
Expand All @@ -19,7 +19,7 @@ entry:
ret i16 %main_ret, !dbg !14
}

declare !dbg !18 void @mainProg(%mainProg*) section "fn-mainProg:v"
declare !dbg !18 void @mainProg(%mainProg*) section "fn-$RUSTY$mainProg:v"

; Function Attrs: nofree nosync nounwind readnone speculatable willreturn
declare void @llvm.dbg.declare(metadata, metadata, metadata) #0
Expand Down Expand Up @@ -54,9 +54,9 @@ source_filename = "file2.st"

%mainProg = type {}

@mainProg_instance = global %mainProg zeroinitializer, section "var-mainProg_instance:r0", !dbg !0
@mainProg_instance = global %mainProg zeroinitializer, section "var-$RUSTY$mainProg_instance:r0", !dbg !0

define void @mainProg(%mainProg* %0) section "fn-mainProg:v" !dbg !10 {
define void @mainProg(%mainProg* %0) section "fn-$RUSTY$mainProg:v" !dbg !10 {
entry:
call void @llvm.dbg.declare(metadata %mainProg* %0, metadata !13, metadata !DIExpression()), !dbg !14
ret void, !dbg !14
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,9 @@ source_filename = "external_file1.st"

%mainProg = type {}

@mainProg_instance = external global %mainProg, section "var-mainProg_instance:r0"
@mainProg_instance = external global %mainProg, section "var-$RUSTY$mainProg_instance:r0"

define i16 @main() section "fn-main:i16" {
define i16 @main() section "fn-$RUSTY$main:i16" {
entry:
%main = alloca i16, align 2
store i16 0, i16* %main, align 2
Expand All @@ -18,16 +18,16 @@ entry:
ret i16 %main_ret
}

declare void @mainProg(%mainProg*) section "fn-mainProg:v"
declare void @mainProg(%mainProg*) section "fn-$RUSTY$mainProg:v"

; ModuleID = 'external_file2.st'
source_filename = "external_file2.st"

%mainProg = type {}

@mainProg_instance = global %mainProg zeroinitializer, section "var-mainProg_instance:r0"
@mainProg_instance = global %mainProg zeroinitializer, section "var-$RUSTY$mainProg_instance:r0"

define void @mainProg(%mainProg* %0) section "fn-mainProg:v" {
define void @mainProg(%mainProg* %0) section "fn-$RUSTY$mainProg:v" {
entry:
ret void
}
1 change: 1 addition & 0 deletions compiler/section_mangler/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -4,3 +4,4 @@ version = "0.0.1"
edition = "2021"

[dependencies]
nom = "7.1"
21 changes: 19 additions & 2 deletions compiler/section_mangler/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -44,20 +44,25 @@

use std::fmt;

mod parser;

/// The main builder type of this crate. Use it to create mangling contexts, in
/// order to encode and decode binary type information.
// TODO: Add example code for using this builder
#[derive(Debug, PartialEq, Clone)]
pub enum SectionMangler {
Function(FunctionMangler),
Variable(VariableMangler),
}

#[derive(Debug, PartialEq, Clone)]
pub struct FunctionMangler {
name: String,
parameters: Vec<FunctionArgument>,
return_type: Option<Type>,
}

#[derive(Debug, PartialEq, Clone)]
pub struct VariableMangler {
name: String,
ty: Type,
Expand All @@ -72,6 +77,13 @@ impl SectionMangler {
SectionMangler::Variable(VariableMangler { name: name.into(), ty })
}

pub fn name(&self) -> &str {
match self {
SectionMangler::Function(FunctionMangler { name, .. })
| SectionMangler::Variable(VariableMangler { name, .. }) => name,
}
}

pub fn with_parameter(self, param: FunctionArgument) -> SectionMangler {
match self {
SectionMangler::Function(f) => {
Expand Down Expand Up @@ -113,6 +125,7 @@ impl SectionMangler {
// NOTE: This is called `variable_linkage` in the `MemberInfo` struct.

/// We have to encode this because if it changes, the function needs to be reloaded - this is an ABI breakage
#[derive(Debug, PartialEq, Clone)]
pub enum FunctionArgument {
ByValue(Type),
ByRef(Type),
Expand All @@ -129,6 +142,7 @@ impl fmt::Display for FunctionArgument {
}

// TODO: Do we have to encode this? Does that affect ABI? Probably
#[derive(Debug, PartialEq, Clone)]
pub enum StringEncoding {
// TODO: Should we encode this differently? this could cause problems compared to encoding unsigned types
/// Encoded as `8u`
Expand All @@ -148,6 +162,7 @@ impl fmt::Display for StringEncoding {

// This maps directly to the [`DataTypeInformation`] enum in RuSTy - we simply remove some fields and add the ability to encode/decode serialize/deserialize
// TODO: Do we have to handle Generic?
#[derive(Debug, PartialEq, Clone)]
pub enum Type {
/// Encoded as `v`
Void,
Expand Down Expand Up @@ -235,16 +250,18 @@ impl fmt::Display for Type {
}
}

pub const PREFIX: &str = "$RUSTY$";

// TODO: How to encode variadics?
fn mangle_function(FunctionMangler { name, parameters, return_type }: FunctionMangler) -> String {
let mangled = parameters
.into_iter()
/* FIXME: Is that correct? */
.fold(return_type.unwrap_or(Type::Void).to_string(), |mangled, arg| format!("{mangled}[{arg}]"));

format!("{name}:{mangled}")
format!("{PREFIX}{name}:{mangled}")
}

fn mangle_variable(VariableMangler { name, ty }: VariableMangler) -> String {
format!("{name}:{ty}")
format!("{PREFIX}{name}:{ty}")
}
Loading
Loading