6 ms·
While procfs has a lot of historical baggage, sysfs is rather specific about the layout and providing only a single value per file, as plain ASCII, rather than
by st_goliath 4y ago
While procfs has a lot of historical baggage, sysfs is rather specific about the layout and providing only a single value per file, as plain ASCII, rather than using anything complex that has to be parsed. Structure is implemented via the filesystem.
In return, the kernel side API for sysfs is also a lot cleaner and allows to more-or-less expose individual variables as tuning knobs for a driver.
Of course there are edge cases, and there are e.g. some binary interfaces as well (e.g. for providing direct register access, or implementing a firmware upload interface for a device).
ABI compat issues aside, I think that implementing "a standardized [structured] record format" as suggested in the comments here is a rather bad idea, going into exactly the wrong direction by adding complexity rather than reducing it, which would definitely cause even more parsing related issues in the long run.
- ilyt 4y ago>While procfs has a lot of historical baggage, sysfs is rather specific about the layout and providing only a single value per file, as plain ASCII, rather than using anything complex that has to be parsed. Structure is implemented via the filesystem. I'd rather have structured file than to have open 30k files (for say conntrack) Hell, just example from the article, /proc/<PID>/stat has 52 parameters. That would be 52 opens and reads with single value per file. > ABI compat issues aside, I think that implementing "a standardized [structured] record format" as suggested in the comments here is a rather bad idea, going into exactly the wrong direction by adding complexity rather than reducing it, which would definitely cause even more parsing related issues in the long run. It's literally the opposite. You have to implement it once on kernel side and once in userspace vs every special format that currently needs
- throwaway09223 4y agoLinux has already half-solved this, eg with netlink. If you're on a system with huge numbers of connections, reading from /proc/net/tcp get extremely slow. Modern tools query connection state using netlink instead (ss vs netstat). This was done by necessity: /proc/net/tcp actually doesn't work at scale. I agree with you, serializing and deserializing files with records is a terrible idea - it cannot be performant. JSON fixes parsing ambiguity but at a cost of being even slower. We already know it won't work. We have already solved this for specific parts of /proc and it works great. All we have to do is finish the work and provide the rest of proc via netlink as well (or whatever else similar non-text based system for querying structured records)
- dale_glass 4y agoJSON can be parsed very quickly: https://github.com/simdjson/simdjson https://github.com/simdjson/simdjson CBOR could be another option: https://en.wikipedia.org/wiki/CBOR https://en.wikipedia.org/wiki/CBOR
- the8472 4y agoJSON cannot be efficient for binary data or even utf8 strings because it needs escaping which means you can't have a zero-copy implementation. CBOR is better in that regard, yeah.
- ilyt 4y agoAll it needs to beat is stringifying and formatting that /proc|/sys already does
- throwaway09223 4y agoIt can't (simdjson is fast compared to other text parsing - it's still extremely slow compared to native types), but that fact actually doesn't matter because the problem isn't the parsing. Even the construction of these text files in proc is too slow. You can't read /proc/net/tcp within a reasonable amount of time on a system with hundreds of thousands of connections. Even allocating/churning memory to store a textual representation becomes a problematic overhead.
- st_goliath 4y ago> You have to implement it once on kernel side and once in userspace I actually did think about this before posting my original response, and I think this is unrealistic from a practical perspective. To elaborate a bit on that: First of, a one-size-fits-all structured format is a lot more complex than a directory with ASCII files in it that each store an integer and IMO invites itself to feature creep (i.e. more complexity). Complexity is IMO the root cause of the issue originally discussed here (if not most bugs). The more code, the more complexity, the more bugs. In my experience, software will always have bugs, complex software more so. There can never be a "one-true-implementation" for userspace. Because of the complexity, people will write their own ad-hoc versions. They "only need that one thing" and don't want to drag the whole library dependency in. Some people think they know better and write their own "lightweight/suckless/..." versions because the kernel one is "bloated", or "that API sucks". Some will rewrite it in their favorite programming language for whatever reason. NIH syndrome, bike shedding, ... Then, what if a widely used implementation has a bug? Especially if it's the "one-true-library" itself? You now need to roll out a fix. Across countless Distros, embedded devices that might get maintenance updates every couple years at best, set-top boxes, network appliances, ... You'll have programs floating around that are statically linked against a specific version of the one-true-library. In the end, we have a variety of differently bugged parsers in use, simply because of the spread in versions alone. The original problem that we wanted to solve, remains. Of course there are issues with the more simplistic approach, but in the case of e.g. sysfs, those are typically corner cases. Adding a one-size-fits-all special, structured format for everything introduces a whole lot of unneeded complexity everywhere else as well. A "one-true-format to solve all problems" that needs special library code for processing IMO introduces a whole lot more problems than it solves.
- touisteur 4y agoBut for conntrack and highly structured commands and data wouldn't you use netlink?