7 ms·
I may be missing the point here but this postings makes little sense to me. There is nothing in the C standard that requires dynamic linking. In fact, I have b
by fefe23 6y ago
I may be missing the point here but this postings makes little sense to me.
There is nothing in the C standard that requires dynamic linking. In fact, I have been creating statically linked binaries with C for decades (and still am).
Also the definition of portability used here is not helpful.
If I take a program and put it on another computer, I can never just expect it to work. The other computer may be running OpenBSD when the first one was running Linux and we are talking about a Windows EXE. This metric makes no sense.
The established meaning of portability is whether you can take the source code and compile it on a different platform (but also supporting a development environment for said programming language), and it will compile and work.
This is not a function of the programming language.
The "winners" of this blog post are winning because they contain compatibility layers. Those work as long as you have one for the target platform. If you don't you may actually be worse off with those languages compared to, say, a basic C environment that does not give you source code portability across all platforms but gives you a workable basis on each platform to bootstrap off of.
Also note that being portable may actually turn out to be a downside, because it means you have to limit what you can do to the common denominator of all supported platforms.
I recommend disregarding this blog post.
- pdonis 6y ago> The established meaning of portability is whether you can take the source code and compile it on a different platform Even this meaning only applies to compiled languages. If I want to run Python code, I don't need to compile it and I don't need a laundry list of supporting tools for compiling and linking; I just need the Python interpreter. Which runs on all common platforms and plenty of uncommon ones.
- taeric 6y agoThis is easy to tease out. Portability can be describing compilation or evaluation/interpretation. Take your python example, you don't just need the interpreter. You also need any supporting infrastructure that the libraries used will need. As a trite example, anything that reads from a camera will need a camera available to work. Indeed, some will need specific cameras, if they don't have a portability later. :) As such, portable goes across many layers and cannot be described at just the language level. Not even at a runtime level.
- pdonis 6y ago> You also need any supporting infrastructure that the libraries used will need. This will also be true of a program in a compiled language, so I don't see that it differentiates between different languages.
- taeric 6y agoI felt I was progressing your point. You can't answer if a program is portable based solely on the language.
- throwaway894345 6y agoYou’re referring to a different definition of “portables than the concept TFA appears to be describing. Within the scope of TFA’s definition, a language (or more precisely, an implementation) absolutely can be portable. Any implementation that can bundle all dependencies (including the runtime) into a single artifact can said to be portable per TFA’s definition of the term. Python could even be portable in this sense if it could zip up the interpreter, libraries, and all so files (however, these bundles would be hundreds of megabytes compressed in practice).
- taeric 6y agoBut that is a shit definition. :) Portability has to take into account the scope of where it will be ported to. And, often, porting the software is something that has to be done. It will not be an intrinsic of the language or the program, but work that was done for them. Is why SCUMM is probably the most ported software. Was not necessarily an intrinsic property of the engine; though, it clearly had affordances that helped. Really, I think Linux shot down a large part of the portability debate. It was made to be non portable. And now it has been ported everywhere.
- throwaway894345 6y agoAgain, I think you're just insisting on evaluating the article based on your own definition of "portability". Note that I agree that your definition is more standard, and the confusion is attributable to the author choosing to overload that term. Let's imagine that the author used a different term--say, distributability--and defined it as something like "how easy it is to get cross-platform software up and running on another system" and the context is "desktop and server computing" as opposed to embedded or whathaveyou. I think this is a perfectly useful criteria for evaluating programming languages (which isn't to say that it's the most important or even very important, only that it's useful). It's useful to know whether I'm going to have a very easy time distributing software (e.g., a self-contained static binary) or a very hard time (e.g., I need to get my non-technical colleague to install brew, use brew to install the right version of python, create a virtualenv, install dependencies--probably including various C dependencies that pip doesn't know about, and then install my application). This isn't a hypothetical consideration; it's an important consideration for me whenever I'm creating internal tools. However, to your point, this isn't helpful for figuring out which languages are going to be able to be deployed to the widest breadth of architectures. They're simply different ideas.
- throwaway894345 6y agoYou need the Python interpreter and all of your dependencies including the many shared objects that Python programs tend to depend on. Moreover, having the right version of the Python interpreter installed is frequently a problem--lots of systems still have Python 2 installed by default and even having Python 3 isn't a guarantee since many programs depend on relatively recent versions of the interpreter which are rarely installed by default on the target system. Note also that while the Python interpreter runs on plenty of uncommon platforms, relatively few packages in the ecosystem do because the ecosystem depends so heavily on C-extensions and `pip install`s of these packages often need to build from source which often assumes you have various headers and libraries installed on your system at certain locations--which is to say the assumption is that you're pip installing onto a "common platform". In my opinion (and extensive experience), I'd rather have something like Go where I can trivially cross compile for whatever `(arch, os)` tuple I want to target and send the resultant binary without concerning myself with runtime dependencies (including the runtime itself).
- mikewarot 6y agoI tried pulling a C program from 2002 into the present world, it was a nightmare. C assumes word size, Macro functioning and the libraries are all radically different, it wouldn't even compile. C is definitely not portable. I had some Pascal code from 1994, when 16/32 bits ruled the world, I compiled/ran it in 64 bit glory, I did have to take out the one assembly optimization I wrote back then. If there were Lazarus/Free Pascal for the new Apple Silicon, I have no doubt that code would work there as well, with zero changes.
- megameter 6y agoRegarding linking: you seem to be conflating concerns with libc's portability with the linking of libc. Libc is a portability concern not because of linking but because it is a worse-is-better compatibility layer. There isn't just one example of it, and it straddles the boundaries of the language ecosystem and the operating environment. If I write C targeting WASM and try to call fopen(), the build system either has to say "no" somewhere along the way, or bamboozle me with a very specific interpretation of what I mean by that, effectively turning it into an unspecified interface. When a language builds on that foundation it gains temporary convenience but misses out on being more encompassing in its approach to compatibility. Your statement only makes sense within a "libc is just the standard" worldview, which I believe contributes to the fragility problem by offloading compatibility into a series of "good-enough" measures instead of documentable specifications.
- elcritch 6y agoThe list certainly is confusing. It took reading it a couple of times, but now it makes more sense what they appear to be basing the list on. Most C builds default to dynamic linking, so while it's trivial it does take a few tweaks. Though that relies almost more heavily on the particular build system used with C. Actually in that regard Nim should be listed the same as C, as I had to pass a few C compiler options recently to allow running an executable compiled on Linux on amd64 to run on x86 Linux as well. So compared to Go's skipping of libc it'd seem to make sense. Maybe it'd be more obvious if the portability was an effort rating from 1-5. Go is 1, simple C is 2, Nim is a 2, and Rust is a 3, and complex/ancient C autoconf/make anywhere from 2-5. Elixir 2-3, Python 4-5. Based largely on the googling efforts I've done in the past. Regarding the compatibility layer though, the bootstrapping makes sense. Generally C and C compilers are going to be imminently more portable since some variant of C is likely yo be available. Python's standard library is likely going to be an enormous effort to port. Perl/Lua much less so but at the expense of the compatibility layer meaning more individual platform work. Most compatibility layers are going to be a pain or limiting as you say. I'd like to say I'm a fan of Nim's "open architecture" standard library (compatibility layer) having recently done a PR to add support for FreeRTOS. Much of the stdlib worked without modification due to "lazy compiling" of code, including the stdlib. It only tries compiling what you use. Skip the default networking and write a few C/C++ FFI calls networking for the platform and you've got a full library of containers, json parsing, etc. Then you can pretty easily add support for Nim networking compatibility later. For example the 'selector' library has support for various OS specific from ancient 'select' to 'epoll' to whatever Windows does based on what you choose to import. Pretty awesome for embedded. Overall it seems the article is considering portability in two narrow contexts. However, having both tried to ship say a scientific GUI program for non-technical users (e.g. using Python QT) on one hand the first definition is useful, while porting code to embedded projects the other can be useful.