From 28d44f2bbf71e20a2046e13c216813c33398deb2 Mon Sep 17 00:00:00 2001 From: Lucia Ceionia Date: Thu, 4 Dec 2025 00:45:42 -0600 Subject: [PATCH] day 4 --- .gitignore | 1 + Makefile | 23 ++++-- day0.h | 92 ++++++++++++++++++++++ day1.c | 67 +++++++++++++++- day2.c | 8 +- day2_plasl.c | 130 +++++++++++++++++++++++++++++++ day3.c | 14 ++-- day4.c | 207 +++++++++++++++++++++++++++++++++++++++++++++++++ lib.h | 43 +++++++--- musl/COPYRIGHT | 193 +++++++++++++++++++++++++++++++++++++++++++++ musl/memcpy.s | 25 ++++++ musl/memset.s | 72 +++++++++++++++++ start.s | 7 ++ 13 files changed, 851 insertions(+), 31 deletions(-) create mode 100644 day0.h create mode 100644 day2_plasl.c create mode 100644 day4.c create mode 100644 musl/COPYRIGHT create mode 100644 musl/memcpy.s create mode 100644 musl/memset.s create mode 100644 start.s diff --git a/.gitignore b/.gitignore index 8ce1ee0..fc87b04 100644 --- a/.gitignore +++ b/.gitignore @@ -1,4 +1,5 @@ *.txt *.elf +*.o blink.log compile_commands.json diff --git a/Makefile b/Makefile index d03c09a..9afc600 100644 --- a/Makefile +++ b/Makefile @@ -2,14 +2,27 @@ FILES = $(wildcard ./*) SRCS = $(filter %.c,$(FILES)) BINS = $(SRCS:%.c=%.elf) -CFLAGS = -Wall -Werror -pedantic -Wno-unused -D_GNU_SOURCE -std=gnu2y\ - -O3 -g -Ttext=C475000 -static -nostartfiles -fno-stack-protector\ - -march=x86-64 -msse2 -msse3 -mssse3 -mpclmul -mpopcnt -madx -mbmi2 -mrdrnd -mrdseed +MUSLFILES = $(wildcard ./musl/*) +MUSLSRCS = $(filter %.s,$(MUSLFILES)) +MUSLOBJS = $(MUSLSRCS:%.s=%.o) + +CFLAGS = -Wall -Werror -pedantic -Wno-unused -std=gnu2y\ + -O3 -c -g -fno-stack-protector -fno-pie\ + -fno-semantic-interposition -fno-trapping-math\ + -march=x86-64 -mprefer-vector-width=128 -mpopcnt -malign-data=compat -malign-stringops + +LFLAGS = -Ttext=C475000 -static -nostdlib -no-pie all: $(BINS) -%.elf: %.c +%.elf: %.o start.o | %.c lib.h $(MUSLOBJS) + ld -o $@ $(LFLAGS) start.o $< $(MUSLOBJS) + +start.o: start.s + nasm -f elf64 -o $@ $< + +%.o: %.c gcc-tree -o $@ $(CFLAGS) $< clean: - rm ./*.elf + rm -f *.elf *.o diff --git a/day0.h b/day0.h new file mode 100644 index 0000000..ad35655 --- /dev/null +++ b/day0.h @@ -0,0 +1,92 @@ +#include "lib.h" + +#define DBG 0 + +static +unsigned char input[] = { +#embed "day0_input.txt" +}; + +static +unsigned char test[] = { +#embed "day0_test.txt" +}; + + +static +unsigned long do_part1(size_t file_len, unsigned char file[file_len]) { + unsigned char *s = file; + unsigned long result = 0; + +#if DBG + print("\n"); +#endif + +do { + s++; +} while (s != &file[file_len]); + + return result; +} + +static +unsigned long do_part2(size_t file_len, unsigned char file[file_len]) { + unsigned char *s = file; + unsigned long result = 0; + +#if DBG + print("\n"); +#endif + +do { + s++; +} while (s != &file[file_len]); + + return result; +} + +#define RUN_TEST1 1 +#define RUN_PART1 0 +#define RUN_TEST2 0 +#define RUN_PART2 0 + +#define TEST1_EXPECT -1 +#define TEST2_EXPECT -1 + +void run() { +#if RUN_TEST1 + print("PART 1 TEST: "); + if (unsigned long v = do_part1(countof(test), test); v != TEST1_EXPECT) { + print("FAILED (got "); + printd(v); + print(", expected " xstr(TEST1_EXPECT) ")\n"); + } else { + print("PASSED\n"); + } +#endif + +#if RUN_PART1 + print("PART 1 RESULT: "); + printd(do_part1(countof(input), input)); + print("\n"); +#endif + +#if RUN_TEST2 + print("PART 2 TEST: "); + if (unsigned long v = do_part2(countof(test), test); v != TEST2_EXPECT) { + print("FAILED (got "); + printd(v); + print(", expected " xstr(TEST2_EXPECT) ")\n"); + } else { + print("PASSED\n"); + } +#endif + +#if RUN_PART2 + print("PART 2 RESULT: "); + printd(do_part2(countof(input), input)); + print("\n"); +#endif + + exit_group(0); +} diff --git a/day1.c b/day1.c index fccb42c..f5eada0 100644 --- a/day1.c +++ b/day1.c @@ -1,4 +1,65 @@ -#include "lib.h" +#include +#include +#include +#include + +#define SYS_write 1 +#define SYS_exit_group 231 + +#define STDOUT_FILENO 1 + +static +void write(uint64_t fileno, void *buffer, size_t len) { + uint64_t a,d; + asm volatile("syscall" + :"=a"(a),"=d"(d):"a"(SYS_write),"D"(fileno),"S"(buffer),"d"(len):"memory"); +} + +[[noreturn]] static +void exit_group() { + asm volatile( + "syscall\n" + "ud2" + ::"a"(SYS_exit_group),"D"(0)); + for (;;); +} + +#define xstr(s) str(s) +#define str(s) #s + +static +void print_many_char(size_t len, char chars[len]) { + write(STDOUT_FILENO, chars, len); +} + +#define print(string) print_many_char(sizeof(string)-1, string) + +static +void printd(unsigned long v) { + if (!v) { + print("0"); + return; + } + char buf[32]; + char *p = buf+32; + unsigned count = 0; + while (v) { + p--; + *p = '0' + (v % 10); + v /= 10; + count++; + } + write(STDOUT_FILENO, p, count); +} + +static +unsigned grabnum(const char *s, const char **end) { + unsigned r = 0; + for (; *s >= '0' && *s <= '9'; s++) + r = r * 10 + (*s - '0'); + *end = s; + return r; +} #define DBG 1 @@ -74,7 +135,7 @@ unsigned do_part2(size_t src_len, const char src[src_len]) { return count; } -void _start() { +void run() { #if RUN_TEST1 print("PART 1 TEST: "); if (unsigned long v = do_part1(countof(test), test); v != TEST1_EXPECT) { @@ -109,5 +170,5 @@ void _start() { print("\n"); #endif - syscall(SYS_exit_group, 0); + exit_group(); } diff --git a/day2.c b/day2.c index 81204eb..5004e81 100644 --- a/day2.c +++ b/day2.c @@ -251,13 +251,13 @@ no_len_change: #define RUN_TEST1 1 #define RUN_PART1 1 -#define RUN_TEST2 1 -#define RUN_PART2 1 +#define RUN_TEST2 0 +#define RUN_PART2 0 #define TEST1_EXPECT 0x1227775554l #define TEST2_EXPECT 0x4174379265l -void _start() { +void run() { #if RUN_TEST1 print("PART 1 TEST: "); if (bcdint v = do_part1(countof(test), test); v != TEST1_EXPECT) { @@ -292,5 +292,5 @@ void _start() { print("\n"); #endif - syscall(SYS_exit_group, 0); + exit_group(0); } diff --git a/day2_plasl.c b/day2_plasl.c new file mode 100644 index 0000000..6a6cd82 --- /dev/null +++ b/day2_plasl.c @@ -0,0 +1,130 @@ +#include "lib.h" + +#define DBG 0 + +static +unsigned char input[] = { +#embed "day2_input.txt" +}; + +static +unsigned char test[] = { +#embed "day2_test.txt" +}; + +uint64_t ipow(uint64_t a, uint64_t b) { + uint64_t m = a; + for (;b;b--) m += a; + return m; +} + +static +uint64_t range(uint64_t start, uint64_t end, uint64_t len) { +#if DBG + print("==\n"); + printd(start); print(" "); printd(end); print("\n"); +#endif + + if ((len & 1) == 1) { + return 0; + } + + uint64_t divisor = ipow(10, len / 2); + + uint64_t first = (start + divisor - 1) / divisor; + uint64_t second = end / divisor; + +#if DBG + print("\n"); + printd(divisor); print("\n"); + printd(first); print(" "); printd(second); print("\n"); +#endif + + uint64_t r = (((second + first) * (second + 1 - first)) / 2) * divisor; + +#if DBG + printd(r); print("\n"); +#endif + + return r; +} + +static +uint64_t do_part1(size_t file_len, unsigned char file[file_len]) { + unsigned char buffer[65535]; + memcpy(buffer, file, file_len); + size_t size = file_len; + buffer[file_len-1] = ','; + + uint64_t out = 0; + uint64_t i = 0; + + while (i < size) { +#if DBG + print("--------------\n"); +#endif + uint64_t startlen = 0, endlen = 0; + uint64_t start = grabnum(buffer+i, NULL); + + while (buffer[i] != '-') { + i++; + startlen++; + } + i++; + + uint64_t end = grabnum(buffer+i, NULL); + + while (buffer[i] != ',') { + i++; + endlen++; + } + i++; + +#if DBG + printd(startlen); print(" "); printd(start); print((char[]){ 10 }); + printd(startlen); print(" "); printd(start); print((char[]){ 10 }); +#endif + + if (endlen != startlen) { + out += range(start, ipow(10, startlen) - 1, startlen) + + range(ipow(10, startlen), end, endlen); + } else { + out += range(start, end, startlen); + } + +#if DBG + print((char[]) { 10 }); +#endif + } + + return out; +} + +#define RUN_TEST1 1 +#define RUN_PART1 1 + +#define TEST1_EXPECT 0x1227775554l + +void run() { + volatile uintptr_t s = (uintptr_t)&s; + printh(s); + print("\n"); +#if RUN_TEST1 + print("PART 1 TEST: "); + if (uint64_t v = do_part1(countof(test), test); v != TEST1_EXPECT) { + print("FAILED (got "); + printd(v); + print(", expected " xstr(TEST1_EXPECT) ")\n"); + } else { + print("PASSED\n"); + } +#endif + +#if RUN_PART1 + print("PART 1 RESULT: "); + printd(do_part1(countof(input), input)); + print("\n"); +#endif + + exit_group(0); +} diff --git a/day3.c b/day3.c index c39c685..8b9c2f5 100644 --- a/day3.c +++ b/day3.c @@ -8,7 +8,7 @@ unsigned char input[] = { }; static -unsigned char test[] = { +unsigned char test_input[] = { #embed "day3_test.txt" }; @@ -78,15 +78,15 @@ unsigned long do_part2(size_t file_len, unsigned char file[file_len]) { return result; } -#define RUN_TEST1 1 -#define RUN_PART1 1 +#define RUN_TEST1 0 +#define RUN_PART1 0 #define RUN_TEST2 1 #define RUN_PART2 1 #define TEST1_EXPECT 357 -#define TEST2_EXPECT 3121910778619 +#define TEST2_EXPECT 3121910778619l -void _start() { +void run() { #if RUN_TEST1 print("PART 1 TEST: "); if (unsigned long v = do_part1(countof(test), test); v != TEST1_EXPECT) { @@ -106,7 +106,7 @@ void _start() { #if RUN_TEST2 print("PART 2 TEST: "); - if (unsigned long v = do_part2(countof(test), test); v != TEST2_EXPECT) { + if (unsigned long v = do_part2(countof(test_input), test_input); v != TEST2_EXPECT) { print("FAILED (got "); printd(v); print(", expected " xstr(TEST2_EXPECT) ")\n"); @@ -121,5 +121,5 @@ void _start() { print("\n"); #endif - syscall(SYS_exit_group, 0); + exit_group(0); } diff --git a/day4.c b/day4.c new file mode 100644 index 0000000..5a2f23a --- /dev/null +++ b/day4.c @@ -0,0 +1,207 @@ +#include "lib.h" + +#define DBG 0 + +static +unsigned char input[] = { +#embed "day4_input.txt" +}; + +static +unsigned char test[] = { +#embed "day4_test.txt" +}; + +static +unsigned char buf[UINT16_MAX]; + +static +unsigned long do_part1(size_t file_len, unsigned char file[file_len]) { + unsigned char *s = file, *d = buf; + unsigned long result = 0; + +#if DBG + print("\n"); +#endif + + unsigned file_stride; + while (*s != '\n') s++; + file_stride = s - file + 1; + s = file; + + unsigned line_count = file_len / file_stride; + + unsigned line_stride = file_stride + 1; + + memset(d, '0', sizeof(buf)); + +#if DBG + printh(file_stride); print("\n"); + printh(line_stride * (line_count + 2)); print("\n"); +#endif + +#if DBG + printns(line_stride, d); print("\n"); +#endif + d += line_stride; + do { + memcpy(d + 1, s, file_stride - 1); +#if DBG + printns(line_stride, d); print("\n"); +#endif + d += line_stride; + s += file_stride; + } while (s != &file[file_len]); +#if DBG + printns(line_stride, d); print("\n"); +#endif + + unsigned char *l = buf + line_stride + 1; + for (unsigned i = line_count; i; i--) { + d = l; + for (unsigned j = line_stride - 2; j; j--) { + if (*d == '@') { + unsigned neighbors = 0 + + (*(d - 1 - line_stride) == '@') + + (*(d - 0 - line_stride) == '@') + + (*(d + 1 - line_stride) == '@') + + (*(d - 1 - 0) == '@') + + (*(d + 1 - 0) == '@') + + (*(d - 1 + line_stride) == '@') + + (*(d - 0 + line_stride) == '@') + + (*(d + 1 + line_stride) == '@'); + if (neighbors < 4) { + result++; + } + } + d++; + } + l += line_stride; + } + + return result; +} + +static +unsigned long do_part2(size_t file_len, unsigned char file[file_len]) { + unsigned char *s = file, *d = buf; + unsigned long result = 0; + +#if DBG + print("\n"); +#endif + + unsigned file_stride; + while (*s != '\n') s++; + file_stride = s - file + 1; + s = file; + + unsigned line_count = file_len / file_stride; + + unsigned line_stride = file_stride + 1; + + memset(d, '0', sizeof(buf)); + +#if DBG + printh(file_stride); print("\n"); + printh(line_stride * (line_count + 2)); print("\n"); +#endif + +#if DBG + printns(line_stride, d); print("\n"); +#endif + d += line_stride; + do { + memcpy(d + 1, s, file_stride - 1); +#if DBG + printns(line_stride, d); print("\n"); +#endif + d += line_stride; + s += file_stride; + } while (s != &file[file_len]); +#if DBG + printns(line_stride, d); print("\n"); +#endif + + unsigned char *l = buf + line_stride + 1; + for (unsigned i = line_count; i; i--) { +line_start: + d = l; + for (unsigned j = line_stride - 2; j; j--) { + if (*d == '@') { + unsigned neighbors = 0 + + (*(d - 1 - line_stride) == '@') + + (*(d - 0 - line_stride) == '@') + + (*(d + 1 - line_stride) == '@') + + (*(d - 1 - 0) == '@') + + (*(d + 1 - 0) == '@') + + (*(d - 1 + line_stride) == '@') + + (*(d - 0 + line_stride) == '@') + + (*(d + 1 + line_stride) == '@'); + if (neighbors < 4) { + *d = '.'; + result++; + if (i > line_count-1) { + i = line_count; + l = buf + line_stride + 1; + goto line_start; + } else { + i += 1; + l -= line_stride * 1; + goto line_start; + } + } + } + d++; + } + l += line_stride; + } + + return result; +} + +#define RUN_TEST1 1 +#define RUN_PART1 1 +#define RUN_TEST2 1 +#define RUN_PART2 1 + +#define TEST1_EXPECT 13 +#define TEST2_EXPECT 43 + +void run() { +#if RUN_TEST1 + print("PART 1 TEST: "); + if (unsigned long v = do_part1(countof(test), test); v != TEST1_EXPECT) { + print("FAILED (got "); + printd(v); + print(", expected " xstr(TEST1_EXPECT) ")\n"); + } else { + print("PASSED\n"); + } +#endif + +#if RUN_PART1 + print("PART 1 RESULT: "); + printd(do_part1(countof(input), input)); + print("\n"); +#endif + +#if RUN_TEST2 + print("PART 2 TEST: "); + if (unsigned long v = do_part2(countof(test), test); v != TEST2_EXPECT) { + print("FAILED (got "); + printd(v); + print(", expected " xstr(TEST2_EXPECT) ")\n"); + } else { + print("PASSED\n"); + } +#endif + +#if RUN_PART2 + print("PART 2 RESULT: "); + printd(do_part2(countof(input), input)); + print("\n"); +#endif + + exit_group(0); +} diff --git a/lib.h b/lib.h index c15d826..3f358b3 100644 --- a/lib.h +++ b/lib.h @@ -1,11 +1,30 @@ #pragma once -#include +#include #include -#include -#include #include #include +#define SYS_write 1 +#define SYS_exit_group 231 + +#define STDOUT_FILENO 1 + +static +void write(uint64_t fileno, void *buffer, size_t len) { + uint64_t a,d; + asm volatile("syscall" + :"=a"(a),"=d"(d):"a"(SYS_write),"D"(fileno),"S"(buffer),"d"(len):"memory"); +} + +[[noreturn]] static +void exit_group(uint64_t code) { + asm volatile( + "syscall\n" + "ud2" + ::"a"(SYS_exit_group),"D"(code)); + for (;;); +} + #define xstr(s) str(s) #define str(s) #s @@ -13,7 +32,7 @@ typedef uint64_t bcdint; static void printns(size_t len, unsigned char chars[len]) { - syscall(SYS_write, STDOUT_FILENO, chars, len); + write(STDOUT_FILENO, chars, len); } static @@ -29,12 +48,12 @@ void printptr(uintptr_t v) { } v >>= 4; } - syscall(SYS_write, STDOUT_FILENO, p, countof(buf)); + write(STDOUT_FILENO, p, countof(buf)); } static void print_many_char(size_t len, char chars[len]) { - syscall(SYS_write, STDOUT_FILENO, chars, len); + write(STDOUT_FILENO, chars, len); } #define print(string) print_many_char(sizeof(string)-1, string) @@ -54,7 +73,7 @@ void printd(unsigned long v) { v /= 10; count++; } - syscall(SYS_write, STDOUT_FILENO, p, count); + write(STDOUT_FILENO, p, count); } static @@ -76,7 +95,7 @@ void printh(unsigned long v) { v >>= 4; count++; } - syscall(SYS_write, STDOUT_FILENO, p, count); + write(STDOUT_FILENO, p, count); } static @@ -95,7 +114,7 @@ void print_hex_char(unsigned char v) { buf[1] = 'A' - 0xA + (v & 0x0F); } - syscall(SYS_write, STDOUT_FILENO, buf, sizeof(buf)); + write(STDOUT_FILENO, buf, sizeof(buf)); } static @@ -125,11 +144,11 @@ bcdint grabbcd(unsigned char *s, unsigned char **end) { } static -unsigned grabnum(const char *s, const char **end) { - unsigned r = 0; +unsigned long grabnum(unsigned char *s, unsigned char **end) { + unsigned long r = 0; for (; *s >= '0' && *s <= '9'; s++) r = r * 10 + (*s - '0'); - *end = s; + if (end) *end = s; return r; } diff --git a/musl/COPYRIGHT b/musl/COPYRIGHT new file mode 100644 index 0000000..2f15edc --- /dev/null +++ b/musl/COPYRIGHT @@ -0,0 +1,193 @@ +musl as a whole is licensed under the following standard MIT license: + +---------------------------------------------------------------------- +Copyright © 2005-2020 Rich Felker, et al. + +Permission is hereby granted, free of charge, to any person obtaining +a copy of this software and associated documentation files (the +"Software"), to deal in the Software without restriction, including +without limitation the rights to use, copy, modify, merge, publish, +distribute, sublicense, and/or sell copies of the Software, and to +permit persons to whom the Software is furnished to do so, subject to +the following conditions: + +The above copyright notice and this permission notice shall be +included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. +IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY +CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, +TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE +SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +---------------------------------------------------------------------- + +Authors/contributors include: + +A. Wilcox +Ada Worcester +Alex Dowad +Alex Suykov +Alexander Monakov +Andre McCurdy +Andrew Kelley +Anthony G. Basile +Aric Belsito +Arvid Picciani +Bartosz Brachaczek +Benjamin Peterson +Bobby Bingham +Boris Brezillon +Brent Cook +Chris Spiegel +Clément Vasseur +Daniel Micay +Daniel Sabogal +Daurnimator +David Carlier +David Edelsohn +Denys Vlasenko +Dmitry Ivanov +Dmitry V. Levin +Drew DeVault +Emil Renner Berthing +Fangrui Song +Felix Fietkau +Felix Janda +Gianluca Anzolin +Hauke Mehrtens +He X +Hiltjo Posthuma +Isaac Dunham +Jaydeep Patil +Jens Gustedt +Jeremy Huntwork +Jo-Philipp Wich +Joakim Sindholt +John Spencer +Julien Ramseier +Justin Cormack +Kaarle Ritvanen +Khem Raj +Kylie McClain +Leah Neukirchen +Luca Barbato +Luka Perkov +Lynn Ochs +M Farkas-Dyck (Strake) +Mahesh Bodapati +Markus Wichmann +Masanori Ogino +Michael Clark +Michael Forney +Mikhail Kremnyov +Natanael Copa +Nicholas J. Kain +orc +Pascal Cuoq +Patrick Oppenlander +Petr Hosek +Petr Skocik +Pierre Carrier +Reini Urban +Rich Felker +Richard Pennington +Ryan Fairfax +Samuel Holland +Segev Finer +Shiz +sin +Solar Designer +Stefan Kristiansson +Stefan O'Rear +Szabolcs Nagy +Timo Teräs +Trutz Behn +Will Dietz +William Haddon +William Pitcock + +Portions of this software are derived from third-party works licensed +under terms compatible with the above MIT license: + +The TRE regular expression implementation (src/regex/reg* and +src/regex/tre*) is Copyright © 2001-2008 Ville Laurikari and licensed +under a 2-clause BSD license (license text in the source files). The +included version has been heavily modified by Rich Felker in 2012, in +the interests of size, simplicity, and namespace cleanliness. + +Much of the math library code (src/math/* and src/complex/*) is +Copyright © 1993,2004 Sun Microsystems or +Copyright © 2003-2011 David Schultz or +Copyright © 2003-2009 Steven G. Kargl or +Copyright © 2003-2009 Bruce D. Evans or +Copyright © 2008 Stephen L. Moshier or +Copyright © 2017-2018 Arm Limited +and labelled as such in comments in the individual source files. All +have been licensed under extremely permissive terms. + +The ARM memcpy code (src/string/arm/memcpy.S) is Copyright © 2008 +The Android Open Source Project and is licensed under a two-clause BSD +license. It was taken from Bionic libc, used on Android. + +The AArch64 memcpy and memset code (src/string/aarch64/*) are +Copyright © 1999-2019, Arm Limited. + +The implementation of DES for crypt (src/crypt/crypt_des.c) is +Copyright © 1994 David Burren. It is licensed under a BSD license. + +The implementation of blowfish crypt (src/crypt/crypt_blowfish.c) was +originally written by Solar Designer and placed into the public +domain. The code also comes with a fallback permissive license for use +in jurisdictions that may not recognize the public domain. + +The smoothsort implementation (src/stdlib/qsort.c) is Copyright © 2011 +Lynn Ochs and is licensed under an MIT-style license. + +The x86_64 port was written by Nicholas J. Kain and is licensed under +the standard MIT terms. + +The mips and microblaze ports were originally written by Richard +Pennington for use in the ellcc project. The original code was adapted +by Rich Felker for build system and code conventions during upstream +integration. It is licensed under the standard MIT terms. + +The mips64 port was contributed by Imagination Technologies and is +licensed under the standard MIT terms. + +The powerpc port was also originally written by Richard Pennington, +and later supplemented and integrated by John Spencer. It is licensed +under the standard MIT terms. + +All other files which have no copyright comments are original works +produced specifically for use as part of this library, written either +by Rich Felker, the main author of the library, or by one or more +contibutors listed above. Details on authorship of individual files +can be found in the git version control history of the project. The +omission of copyright and license comments in each file is in the +interest of source tree size. + +In addition, permission is hereby granted for all public header files +(include/* and arch/*/bits/*) and crt files intended to be linked into +applications (crt/*, ldso/dlstart.c, and arch/*/crt_arch.h) to omit +the copyright notice and permission notice otherwise required by the +license, and to use these files without any requirement of +attribution. These files include substantial contributions from: + +Bobby Bingham +John Spencer +Nicholas J. Kain +Rich Felker +Richard Pennington +Stefan Kristiansson +Szabolcs Nagy + +all of whom have explicitly granted such permission. + +This file previously contained text expressing a belief that most of +the files covered by the above exception were sufficiently trivial not +to be subject to copyright, resulting in confusion over whether it +negated the permissions granted in the license. In the spirit of +permissive licensing, and of not having licensing issues being an +obstacle to adoption, that text has been removed. diff --git a/musl/memcpy.s b/musl/memcpy.s new file mode 100644 index 0000000..3d960ef --- /dev/null +++ b/musl/memcpy.s @@ -0,0 +1,25 @@ +.global memcpy +.global __memcpy_fwd +.hidden __memcpy_fwd +.type memcpy,@function +memcpy: +__memcpy_fwd: + mov %rdi,%rax + cmp $8,%rdx + jc 1f + test $7,%edi + jz 1f +2: movsb + dec %rdx + test $7,%edi + jnz 2b +1: mov %rdx,%rcx + shr $3,%rcx + rep + movsq + and $7,%edx + jz 1f +2: movsb + dec %edx + jnz 2b +1: ret diff --git a/musl/memset.s b/musl/memset.s new file mode 100644 index 0000000..2d3f5e5 --- /dev/null +++ b/musl/memset.s @@ -0,0 +1,72 @@ +.global memset +.type memset,@function +memset: + movzbq %sil,%rax + mov $0x101010101010101,%r8 + imul %r8,%rax + + cmp $126,%rdx + ja 2f + + test %edx,%edx + jz 1f + + mov %sil,(%rdi) + mov %sil,-1(%rdi,%rdx) + cmp $2,%edx + jbe 1f + + mov %ax,1(%rdi) + mov %ax,(-1-2)(%rdi,%rdx) + cmp $6,%edx + jbe 1f + + mov %eax,(1+2)(%rdi) + mov %eax,(-1-2-4)(%rdi,%rdx) + cmp $14,%edx + jbe 1f + + mov %rax,(1+2+4)(%rdi) + mov %rax,(-1-2-4-8)(%rdi,%rdx) + cmp $30,%edx + jbe 1f + + mov %rax,(1+2+4+8)(%rdi) + mov %rax,(1+2+4+8+8)(%rdi) + mov %rax,(-1-2-4-8-16)(%rdi,%rdx) + mov %rax,(-1-2-4-8-8)(%rdi,%rdx) + cmp $62,%edx + jbe 1f + + mov %rax,(1+2+4+8+16)(%rdi) + mov %rax,(1+2+4+8+16+8)(%rdi) + mov %rax,(1+2+4+8+16+16)(%rdi) + mov %rax,(1+2+4+8+16+24)(%rdi) + mov %rax,(-1-2-4-8-16-32)(%rdi,%rdx) + mov %rax,(-1-2-4-8-16-24)(%rdi,%rdx) + mov %rax,(-1-2-4-8-16-16)(%rdi,%rdx) + mov %rax,(-1-2-4-8-16-8)(%rdi,%rdx) + +1: mov %rdi,%rax + ret + +2: test $15,%edi + mov %rdi,%r8 + mov %rax,-8(%rdi,%rdx) + mov %rdx,%rcx + jnz 2f + +1: shr $3,%rcx + rep + stosq + mov %r8,%rax + ret + +2: xor %edx,%edx + sub %edi,%edx + and $15,%edx + mov %rax,(%rdi) + mov %rax,8(%rdi) + sub %rdx,%rcx + add %rdx,%rdi + jmp 1b diff --git a/start.s b/start.s new file mode 100644 index 0000000..7d5d495 --- /dev/null +++ b/start.s @@ -0,0 +1,7 @@ +extern run +global _start +_start: +sub rsp,0x1000 +and rsp,~0xfff +call run +ud2