10-07-10 - Portable CRT God Dammit

What a god damn disaster. How is it that none of us have made our old portable wrapper for the CRT? I want a standard interface to the functions that do exist, and a standard way to ask for "does this exist", eg. something like :

#if fseek64_exists



int32 off32 = check_value_cast_throw<int32>(off64);


Mostly it should just be a wrapper that passes through to the underlying CRT, but for some things that are platform independent (eg. string stuff, sprintfs, etc.) it could just be its own implementation.

I see that Sean has started a portable types header called sophist that gives you sized types (int16 etc) and some #defines to check to get info about your platform. That's a good start.

For speed work you'd like some more things like "size of register" and something like "intr" (an int the size of a register) (one big issue here is whether the 64 bit type fits in a register or not). Also things like "can type be used unaligned".

Obviously C99 would help a lot, but even it wouldn't be everything. You want the stuff above that tells you a bit more about your platform and exposes low-level ops a bit. You also want stuff that's at the "POSIX" library level as opposed to just the CRT, eg. dir ops & renames and truncate and chmod and all that kind of stuff.

Every time I do portability work I think "god damn I wish I just made my own portability library" but instead I don't do it and just hack enough to make the current project work. If I had just done it the clean way from the beginning I would have saved a lot of work and been happier and made something that was useful to other people. And.. I'm just doing it the hacky way yet again.

(actually Boost addresses a lot of this but is just sick over-complex and inconsistent in quality; for example Boost.Thread looks pretty good and has Win32 condition variables for example). I also just randomly found this ptypes lib which is pretty good for Win32 vs POSIX implementations of threading stuff.


Jim Tilander said...

Just make your own wrappers, it's always going to pay off. MS just has a insane way of extending things their own way so that you have to bend over backwards to do anything on their platform. All the names are different and 64 bit is just an afterthought.

Doing printf formatting with pointers and 64 bit numbers across multiple platform is a *nightmare* ... yeah, they could have done this better...

Anonymous said...

I have some portability stuff in stb.h but I didn't bother breaking it out.

Because for me the other problem is that the C library has stupid crap like strncpy() which don't really do what you want, so I might as well put better wrappers on those too.

Oh, and hey, for portability I can add an fopen/fclose wrapper that does UTF8 on Windows. And as long as I'm at it, I'll make it write to a temporary file and then the fclose() moves it over the old one.

Oh and as long as I'm doing that, maybe I'll make a file compression thing so I can get 2:1 compression on anything I write if I really want.

And then it mushroomed out of control.

But maybe a just-portability-that's-it-nothing-else would be good.

cbloom said...

Yeah, I have the same problem of adding too much of my own stuff, but then I can't use it in super-low-level applications. The money thing to do would be :

pcrt : just portable crt, no extensions

pcrtplus : add things like strlcpy , strnicmp, vsnwprintf that aren't quite crt but should be

pcrtthread : add portable threading stuff

pcrtpath : add utf8 file stuff and dir listing and such (not just stdio but rename/delete/truncate), cross platform path manipulation

what a mess

old rants