diff options
author | ubq323 <ubq323@ubq323.website> | 2024-04-13 02:16:39 +0100 |
---|---|---|
committer | ubq323 <ubq323@ubq323.website> | 2024-04-13 02:16:39 +0100 |
commit | e4b1dd28018a3462334c695dc11bd0e0f1e8122a (patch) | |
tree | b07eb3e9ccaae332c542bcccce89b5ff26181fa6 | |
parent | 0fc5f56e6287541901dc956115f44e9bad93279d (diff) |
load image data from files on startup
-rw-r--r-- | server/main.ha | 63 |
1 files changed, 54 insertions, 9 deletions
diff --git a/server/main.ha b/server/main.ha index ae7d9eb..30e5e0a 100644 --- a/server/main.ha +++ b/server/main.ha @@ -14,6 +14,7 @@ use unix::poll; use drawing; use drawing::{pos}; use packet_reader; +use bytes; def PORT: u16 = 41460; @@ -31,17 +32,11 @@ export fn main() void = { let pictures: []drawing::picture = alloc([],len(offs)); for (let i = 0z; i < len(offs); i +=1){ - append(pictures, drawing::picture { - w = CHUNKSIZE, - h = CHUNKSIZE, - d = alloc([0...],CHUNKSIZE*CHUNKSIZE: size): *[*]u32, - world_pos = offs[i], - }); + append(pictures, load_picture_from_file(offs[i])!); }; - for (const p &.. pictures) drawing::clear_picture(p, 0xffffff); - const listener = match(tcp::listen(ip::ANY_V4, PORT)) { + const listener = match(tcp::listen(ip::ANY_V4, PORT, tcp::reuseaddr)) { case let err: net::error => fmt::fatalf(net::strerror(err)); case let sock: net::socket => @@ -53,10 +48,14 @@ export fn main() void = { def save_interval = 20 * time::SECOND; +// caller should free return value +fn filename_from_world_pos(pos: pos) str = + fmt::asprintf("./c.{}.{}.ppm",pos.0,pos.1); + fn save_world(pictures: []drawing::picture) void = { fmt::printfln("saving world!")!; for (const pic &.. pictures) { - const filename = fmt::asprintf("./c.{}.{}.ppm",pic.world_pos.0, pic.world_pos.1); + const filename = filename_from_world_pos(pic.world_pos); fmt::printfln("\t-> {}",filename)!; defer free(filename); const mode = fs::mode::USER_RW | fs::mode::GROUP_RW; @@ -83,6 +82,52 @@ fn save_world(pictures: []drawing::picture) void = { }; +type bad_header = !void; +fn load_picture_from_file(world_pos: pos) (drawing::picture | fs::error | bad_header) = { + const filename = filename_from_world_pos(world_pos); + defer free(filename); + const file = os::open(filename)?; + fmt::printfln("reading from {}",filename)!; + defer { + fmt::printfln("closing {}",filename)!; + match (io::close(file)) { + case let err: io::error => fmt::println("error",io::strerror(err))!; + case => yield; + }; + }; + + const header = fmt::asprintf("P6\n{} {}\n{}\n",CHUNKSIZE,CHUNKSIZE,255); + defer free(header); + const header_bytes = strings::toutf8(header); + let header_buf: []u8 = alloc([0...],len(header_bytes)); + defer free(header_buf); + io::readall(file, header_buf)?; + if (!bytes::equal(header_buf, header_bytes)) return bad_header; + + let file_buf: []u8 = alloc([0...], 3*CHUNKSIZE*CHUNKSIZE); + defer free(file_buf); + io::readall(file, file_buf)?; + let picture_buf: []u32 = alloc([0...], CHUNKSIZE*CHUNKSIZE); + for (let i = 0z; i < len(picture_buf); i += 1) { + picture_buf[i] = (file_buf[3*i]:u32<<16) + |(file_buf[3*i+1]:u32<<8) + |(file_buf[3*i+2]:u32); + if (picture_buf[i] != 0xffffff) fmt::println(i,picture_buf[i])!; + }; + return drawing::picture { + w = CHUNKSIZE, + h = CHUNKSIZE, + d = picture_buf: *[*]u32, + world_pos = world_pos, + }; +}; + + + + + + + fn loop(listener: net::socket, pictures: []drawing::picture) void = { // pollfds[0] is the listener // pollfds[n>0] corresponds to packet_readers[n-1] |