tag:blogger.com,1999:blog-22402839077296303322024-03-14T05:37:46.420+01:00((nil) is (not(null)))Random-osity about computers and games and politics and life and stuff.Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.comBlogger151125tag:blogger.com,1999:blog-2240283907729630332.post-67379391011438855492021-06-17T16:04:00.000+02:002021-06-17T16:04:33.498+02:00Otherworld Miniatures<p>I ordered a bunch of miniatures from <a href="https://otherworldminiatures.co.uk/" target="_blank">Otherworld Miniatures</a> in the United Kingdom. I had been interested in their stuff for a while but failed to order before the whole BREXIT thing took effect. So I figured this would be a good experiment to see how "ordering from the UK" works for folks in Europe now. Here are the basic facts for my order:</p>
<ul><li>May 25, 2021: Order filed and Paypal authorized for £54.50 GBP.</li><li>June 8, 2021: Email confirming order is complete.</li><li>June 17, 2021: Package arrives at my house around noon.</li></ul>
<p>I am not complaining about anything here, the order wasn't urgent and no particular delivery date had been promised as far as I know. I do, however, want to point out that a June 1, 2021 email I had sent was completely ignored, so that wasn't great.</p>
<p>Here we go with the entirely predictable "unboxing" photos you've all been waiting for! First the outside...</p>
<table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto;"><tbody><tr><td style="text-align: center;"><a href="https://1.bp.blogspot.com/-Yt3RxPqxRWs/YMtSB_V_jmI/AAAAAAAADX8/vRg4oaK5NIgSv9ORv53kPbDB5yCxlkiaQCLcBGAsYHQ/s1024/IMG_20210617_140940303-fuzz-color-small.jpg" style="margin-left: auto; margin-right: auto;"><img border="0" data-original-height="768" data-original-width="1024" height="300" src="https://1.bp.blogspot.com/-Yt3RxPqxRWs/YMtSB_V_jmI/AAAAAAAADX8/vRg4oaK5NIgSv9ORv53kPbDB5yCxlkiaQCLcBGAsYHQ/w400-h300/IMG_20210617_140940303-fuzz-color-small.jpg" width="400" /></a></td></tr><tr><td class="tr-caption" style="text-align: center;">The package itself. Air mail? Fancy!</td></tr></tbody></table>
<br />
<table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto;"><tbody><tr><td style="text-align: center;"><a href="https://1.bp.blogspot.com/-OuXcBk1HPKE/YMtSCESpb5I/AAAAAAAADYA/BcS2aFddKb0ESSV-sA6GxnXMMl1VIOjGwCLcBGAsYHQ/s1024/IMG_20210617_141008994-fuzz-color-small.jpg" style="margin-left: auto; margin-right: auto;"><img border="0" data-original-height="1024" data-original-width="768" height="400" src="https://1.bp.blogspot.com/-OuXcBk1HPKE/YMtSCESpb5I/AAAAAAAADYA/BcS2aFddKb0ESSV-sA6GxnXMMl1VIOjGwCLcBGAsYHQ/w300-h400/IMG_20210617_141008994-fuzz-color-small.jpg" width="300" /></a></td></tr><tr><td class="tr-caption" style="text-align: center;">Post-BREXIT necessities.</td></tr></tbody></table>
<p>Now the inside...</p>
<table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto;"><tbody><tr><td style="text-align: center;"><a href="https://1.bp.blogspot.com/-5J6b0jm1StY/YMtSCByIMwI/AAAAAAAADYE/DqAK485jpawwN8pqq9gzS9yDgqOkvJnQwCLcBGAsYHQ/s1024/IMG_20210617_141037437-fuzz-color-small.jpg" style="margin-left: auto; margin-right: auto;"><img border="0" data-original-height="768" data-original-width="1024" height="300" src="https://1.bp.blogspot.com/-5J6b0jm1StY/YMtSCByIMwI/AAAAAAAADYE/DqAK485jpawwN8pqq9gzS9yDgqOkvJnQwCLcBGAsYHQ/w400-h300/IMG_20210617_141037437-fuzz-color-small.jpg" width="400" /></a></td></tr><tr><td class="tr-caption" style="text-align: center;">Hmm... I guess I expected more?</td></tr></tbody></table>
<br />
<table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto;"><tbody><tr><td style="text-align: center;"><a href="https://1.bp.blogspot.com/-w_bLMiXkrzI/YMtSCwDkyII/AAAAAAAADYI/ztnNf1fC6p8-vKEeqjWY8xG9GhgdEZU6ACLcBGAsYHQ/s1024/IMG_20210617_141100480-fuzz-color-small.jpg" style="margin-left: auto; margin-right: auto;"><img border="0" data-original-height="1024" data-original-width="768" height="400" src="https://1.bp.blogspot.com/-w_bLMiXkrzI/YMtSCwDkyII/AAAAAAAADYI/ztnNf1fC6p8-vKEeqjWY8xG9GhgdEZU6ACLcBGAsYHQ/w300-h400/IMG_20210617_141100480-fuzz-color-small.jpg" width="300" /></a></td></tr><tr><td class="tr-caption" style="text-align: center;">I like the note. Good people.</td></tr></tbody></table>
<br />
<table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto;"><tbody><tr><td style="text-align: center;"><a href="https://1.bp.blogspot.com/-npIeteDLOiA/YMtSDDzGlDI/AAAAAAAADYM/tOCV2UWlzcwCY1Txw2P9hev4RQQ_rNyWgCLcBGAsYHQ/s1024/IMG_20210617_141200471-color-small.jpg" style="margin-left: auto; margin-right: auto;"><img border="0" data-original-height="1024" data-original-width="768" height="400" src="https://1.bp.blogspot.com/-npIeteDLOiA/YMtSDDzGlDI/AAAAAAAADYM/tOCV2UWlzcwCY1Txw2P9hev4RQQ_rNyWgCLcBGAsYHQ/w300-h400/IMG_20210617_141200471-color-small.jpg" width="300" /></a></td></tr><tr><td class="tr-caption" style="text-align: center;">No bottom padding. Sad.</td></tr></tbody></table>
<p>Finally, the contents...</p>
<table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto;"><tbody><tr><td style="text-align: center;"><a href="https://1.bp.blogspot.com/-GJjH7f-6zsI/YMtSDU3deZI/AAAAAAAADYQ/mXCnQcjrIX4R25S8QrhTt_XA6S18N4tjQCLcBGAsYHQ/s1024/IMG_20210617_141715896-color-small.jpg" style="margin-left: auto; margin-right: auto;"><img border="0" data-original-height="768" data-original-width="1024" height="300" src="https://1.bp.blogspot.com/-GJjH7f-6zsI/YMtSDU3deZI/AAAAAAAADYQ/mXCnQcjrIX4R25S8QrhTt_XA6S18N4tjQCLcBGAsYHQ/w400-h300/IMG_20210617_141715896-color-small.jpg" width="400" /></a></td></tr><tr><td class="tr-caption" style="text-align: center;">But everything seems to be okay.<br /></td></tr></tbody></table>
<p>Everything seems to have arrived in good condition, despite my misgivings about the lack of all-around padding. Now the hard stuff begins: I am terrible at assembling miniatures. I mean I am even worse at painting them, but I usually only buy "one piece" miniatures because I know about my distinct lack of skills. Oh well, wish me luck! Now where's that glue...?</p>Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com0tag:blogger.com,1999:blog-2240283907729630332.post-81845240041281303062021-06-11T20:35:00.000+02:002021-06-11T20:35:26.372+02:00Third Grade Memory<p>I just made a forum post elsewhere and realized that I should push this "third grade memory" of mine out here as well. Don't worry about the context.</p>
<blockquote><p>In like third grade, in the winter, after school, before
heading home, we'd go over to the church. Lots of low, curved walls with snow on
top there. We'd sketch buttons and screens and stuff into the top of
those walls and we'd play out some Star Trek re-run from the night before. Someone was Kirk and someone was Scotty and so on. We
decided on the fly what we could and could not do and what would happen. We
did this for about thirty minutes to an hour, then went home for lunch
and homework and comics and stuff. When we played next, a day or two
later, we'd keep some of the decisions we made before, others we
redid, new episodes added new information, etc. Nobody wrote any of that down despite us having a grand old
time for weeks of school.</p></blockquote>
<p>Plenty here that sort of dates this of course. Kids these days don't seem to get out of school around lunchtime anymore, instead they are forced to do "pedagogically sound" stuff that others thought up for them in the afternoon. And if that wasn't sad enough, if one of them would actually complain about not liking those "well-designed exercises" they'd get some kids-level psychoanalysis next week. Oh well, I guess it's progress?<br /></p>Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com0tag:blogger.com,1999:blog-2240283907729630332.post-60312525232078442152020-11-11T22:20:00.000+01:002020-11-11T22:20:49.998+01:00Let's hope I am wrong...<p>...but I fear I might not be. Looking at everything that's going on with Trump and his cronies right now, I cannot help but think that their plan is to drag it all out until some state legislatures have to select electors in order to not miss the safe harbor deadline. And of course Republican state legislatures will pick the Republican slates. Combined with another group of cronies waiting in the wings of the Pentagon, the FBI, and the DHS for crowd control, it will be the coup Trump has been playing for all along. He'll finally be able to join the ranks of his pals in other authoritarian societies and keep on ruling until Junior eventually succeeds him. On the upside, we'll actually live in interesting times, just as the old Chinese curse said. Cheers!<br /></p>Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com1tag:blogger.com,1999:blog-2240283907729630332.post-9308396440714254272020-08-11T13:04:00.001+02:002020-08-16T16:58:03.567+02:00OpenBSD IPv6 on TinyKVM<p>I had a lot of trouble getting IPv6 to work under <a href="https://www.openbsd.org/" target="_blank">OpenBSD 6.7</a> on a <a href="https://tinykvm.com/" target="_blank">TinyKVM</a> instance. So here, for reference, is how I finally made it work:</p><ol style="text-align: left;"><li>In your control panel, note the IP addresses for your instance and its gateways; for the IPv6 address of your instance, you get to pick the last 16 bits yourself, but obviously you can't pick the IPv6 of your gateway.</li><li>Edit <span style="font-family: courier;">/etc/hostname.em0</span> and put in the IPv4 (keyword <span style="font-family: courier;">inet</span>) and IPv6 (keyword <span style="font-family: courier;">inet6</span>) addresses (and netmasks) for your instance, nothing else.</li><li>Edit <span style="font-family: courier;">/etc/mygate</span> and put in the IPv4 and IPv6 addresses for your gateways, nothing else.</li><li>Stop and disable the <span style="font-family: courier;">slaacd</span> daemon using <span style="font-family: courier;">rcctl</span>; I guess the <a href="https://openbsd.org/" target="_blank">OpenBSD</a> folks are hopeful that most networks support <a href="https://en.wikipedia.org/wiki/IPv6#Stateless_address_autoconfiguration_(SLAAC)" target="_blank">SLAAC</a> but I had no luck here.<br /></li><li>Try restarting the network using <span style="font-family: courier;">sh /etc/netstart</span> but if that doesn't fix things for you, reboot the instance and hope for the best.</li></ol><p>Note that I had to add a "mystical" invocation of <span style="font-family: courier;">ifconfig</span> to <span style="font-family: courier;">/etc/rc.local</span> as well. Without that, the instance wouldn't pick up either of its IPs immediately on boot but only after a roughly 5 minute delay. No idea what the <a href="https://tinykvm.com/" target="_blank">TinyKVM</a> folks are doing there, but hey, with this "all static" configuration and the weird <span style="font-family: courier;">ifconfig</span> trick things now work roughly as they should. If you figure out a better way of doing this, please let me know! </p>Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com0tag:blogger.com,1999:blog-2240283907729630332.post-19832322611872841472020-07-05T01:57:00.003+02:002020-07-05T01:59:25.965+02:00Hosting OptionsFor various reasons I've been looking around for "new" VPS hosting options again. This is a brief summary of the "neat" things I found. It's not a "review" of any kind, it's literally just a bunch of links and commentary. (If I ever use any of these options for long enough to have an opinion, I'll add a review or three.)<br />
<br />
Historically I've mostly used <a href="https://www.linode.com/" target="_blank">Linode</a>, especially "back in the day" when I was running lots of game servers across the US (and even in the UK for a while); my longest-running (shared) server is also on <a href="https://www.linode.com/" target="_blank">Linode</a>. They have some great tech, nice support, and it's generally very smooth sailing indeed.<br />
<br />
But there are "issues" as well, especially these days. First they don't have a "cheap" storage option. Everything is NVME SSDs these days and so with a small plan (what I usually run because I am cheap) you get 25 GB. Not too shabby if you grew up in the 1970s, but not great either.<br />
<br />
After a bit of research, I noticed that <a href="https://www.ramnode.com/" target="_blank">RamNode</a> actually offers plans with good-old "spinning rust" disks. Yes, the kind some of you don't even remember. As of today, you can get 160 GB for $3/month and 325 GB for $5/month. Pretty sweet if all you need is a bunch of space, for automated backups for example. Of course you need to keep an eye on bandwidth, but hey, here's the storage if you need it.<br />
<br />
Another "issue" is that US companies are, well, <i>US</i> companies. Just like German companies are <i>German</i> and Australian companies are <i>Australian</i>. Doh! What I am getting at is that by picking a hosting company, you're also picking (to a degree) the laws that protect (or not!) your data, privacy, freedom, or life. So depending on what you plan on doing with your VPS, you may want to pick an "exotic" jurisdiction instead of the obvious one.<br />
<br />
I ended up looking at Switzerland, Austria, and Iceland in more detail. From a <a href="https://en.wikipedia.org/wiki/Five_Eyes" target="_blank">"Five (Or More) Eyes"</a> perspective, these are places that at least have no "overt" history of large-scale "illegal" spying. They also have "reasonable" <a href="https://rsf.org/en/ranking" target="_blank">Press Freedom Rankings</a> which can be helpful if you plan to do some investigative reporting online. But don't forget the "small print" of your VPS provider either, different companies have vastly different "Terms of Service" regardless of the level of "freedom" that exists in their respective countries. Also these things are never as simple as shoving your data or services elsewhere, so if in doubt get yourself a lawyer!<br />
<br />For me, <a href="https://www.1984hosting.com/" target="_blank">1984 Hosting</a> in Iceland checks most of the boxes I care about. Also their pricing is a lot better than many other VPS vendors in Iceland. For example they have a reasonable $5/month plan that's actually comparable (except for bandwidth) with a cheap <a href="https://www.linode.com/" target="_blank">Linode</a> plan. On top of that I was impressed by their <a href="https://1984hosting.com/static/files/Crash_Report_of_the_I_O_failure_at_1984_on_15_November_2017.pdf" target="_blank">recent report</a> on a 2017 incident that brought down much of their operation. Yes, maybe it's a little late, but it's certainly detailed and I very much like the idea of them trying to be this transparent about what happened, why it happened, and what they've done to avoid it in the future.<br />
<br />
A final "issue" is operating systems: It's kind of a pain (or at least it used to be, maybe it improved recently?) to install <a href="https://www.openbsd.org/" target="_blank">OpenBSD</a> on <a href="https://www.linode.com/" target="_blank">Linode</a>. Yes, I've been mostly a Linux person for the past 15 years or so, but I've recently "tuned back into" the BSD world a bit more and I like what's happened there. I currently run <a href="https://www.openbsd.org/" target="_blank">OpenBSD</a> on a small <a href="https://www.vultr.com/" target="_blank">Vultr</a> instance and that works reasonably well. But I also found a <a href="https://openbsd.amsterdam/" target="_blank">small outfit in Amsterdam</a> that not only offers <a href="https://www.openbsd.org/" target="_blank">OpenBSD</a> VMs but also uses <a href="https://www.openbsd.org/" target="_blank">OpenBSD</a> to run the virtualization infrastructure itself! On top of that, they donate to the <a href="https://www.openbsd.org/" target="_blank">OpenBSD</a> developers. Their pricing is yearly and works out to $5/month for a small VM (half the RAM of <a href="https://www.linode.com/" target="_blank">Linode</a>, but twice the disk space).<br />
<br />
That's it for me and hosting for now. Feel free to share any hosting tips <b>you</b> have in the comments, I am "all ears" as it were.Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com0tag:blogger.com,1999:blog-2240283907729630332.post-63911958813947768742018-05-01T03:57:00.002+02:002018-05-01T03:57:30.935+02:00Cobalt Qube 2 / RaQ 2 NotesI've had an old <a href="https://en.wikipedia.org/wiki/Cobalt_Qube" target="_blank">Cobalt Qube 2</a> in my possession since at least 2003 and I got my hands on an old <a href="https://en.wikipedia.org/wiki/Cobalt_RaQ" target="_blank">Cobalt RaQ 2</a> sometime in 2007. These are cute ("qute"?) <a href="https://en.wikipedia.org/wiki/R5000" target="_blank">MIPS</a> machines that (used to) work great as targets for my <a href="https://www.cs.jhu.edu/~phf/2018/spring/cs328/" target="_blank">Compilers and Interpreters</a> course. Sadly both boxes have been "out of commission" for a few years, but I recently decided that I want to run them again, the RaQ in particular. In the process I noticed that a few important pieces of Cobalt information are hard to find online these days, so this post is mostly a collection of notes for myself.<br />
<br />
First here are two basic shots of the RaQ 2 in pretty much the state I received it in over 10 years ago. First note the lack of a cover for the power supply! You'll need to be somewhat careful working in here if you're worried about a capacitor zapping you.<br />
<br />
<table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto; text-align: center;"><tbody>
<tr><td style="text-align: center;"><a href="https://1.bp.blogspot.com/-l1PXhVmjORk/Wue12ExskEI/AAAAAAAACls/JDjic-lx3rASC7BSzii8e6WBaKokNMfLwCLcBGAs/s1600/20180209_142015-cut-color.jpg" imageanchor="1" style="margin-left: auto; margin-right: auto;"><img border="0" data-original-height="640" data-original-width="1220" height="208" src="https://1.bp.blogspot.com/-l1PXhVmjORk/Wue12ExskEI/AAAAAAAACls/JDjic-lx3rASC7BSzii8e6WBaKokNMfLwCLcBGAs/s400/20180209_142015-cut-color.jpg" width="400" /></a></td></tr>
<tr><td class="tr-caption" style="text-align: center;">Cobalt RaQ 2 Front</td></tr>
</tbody></table>
<br />
There is also a spot for a fan but apparently the power supply never gets hot enough because (as you can see in the next shot) that grate is actually covered by the Cobalt logo.<br />
<br />
<table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto; text-align: center;"><tbody>
<tr><td style="text-align: center;"><a href="https://1.bp.blogspot.com/-bpeAqkW78WM/Wue12Z8daQI/AAAAAAAAClw/6_yWN-GUdkUPiSOxFZo0Td88TfU_WN79gCLcBGAs/s1600/20180209_141855-cut-color.jpg" imageanchor="1" style="margin-left: auto; margin-right: auto;"><img border="0" data-original-height="683" data-original-width="1220" height="223" src="https://1.bp.blogspot.com/-bpeAqkW78WM/Wue12Z8daQI/AAAAAAAAClw/6_yWN-GUdkUPiSOxFZo0Td88TfU_WN79gCLcBGAs/s400/20180209_141855-cut-color.jpg" width="400" /></a></td></tr>
<tr><td class="tr-caption" style="text-align: center;">Cobalt RaQ 2 Back</td></tr>
</tbody></table>
<br />
The installed fan is <i>incredibly</i> tiny and in my RaQ 2 it doesn't sound particularly healthy anymore. I have not double-checked yet, but <i>supposedly</i> Cobalt used <a href="http://elcodis.com/parts/453033/KDE1235PFB1-8__MS_.html" target="_blank">this SUNON fan</a> for the RaQ 2. Sourcing an exact replacement fan has turned out to be difficult, but I've also found some ancient posts that claim that these machines don't really get hot enough to require a fan in the first place. I am leaving mine in for now, hoping that even if it fails it won't bring down the box with it.<br />
<br />
Next topic: Failed battery. There's a CR2032 located on the main board next to the power supply. Sadly the thing has one of those <i>dreaded</i> sockets with an excessively tight retaining clip on top. You're supposed to "lift the clip" and then slide out the battery, but of course in the process of doing that the <i>entire thing</i> just "ripped off" the mainboard. To add insult to injury, a solder pad came off as well, complete with the attached copper track of course.<br />
<br />
<table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto; text-align: center;"><tbody>
<tr><td style="text-align: center;"><a href="https://3.bp.blogspot.com/-_RGS5zxg74o/WufAvyxn6pI/AAAAAAAACmc/PKbWbPkXmSI73yzzuE339GiXpPZp61b_gCLcBGAs/s1600/20180430_163856-cut-color.jpg" imageanchor="1" style="margin-left: auto; margin-right: auto;"><img border="0" data-original-height="527" data-original-width="611" height="276" src="https://3.bp.blogspot.com/-_RGS5zxg74o/WufAvyxn6pI/AAAAAAAACmc/PKbWbPkXmSI73yzzuE339GiXpPZp61b_gCLcBGAs/s320/20180430_163856-cut-color.jpg" width="320" /></a></td></tr>
<tr><td class="tr-caption" style="text-align: center;">Socket and copper track, yikes!</td></tr>
</tbody></table>
<br />
Witness the complete destruction on the mainboard:<br />
<br />
<table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto; text-align: center;"><tbody>
<tr><td style="text-align: center;"><a href="https://4.bp.blogspot.com/-QiRg2C90bhY/WufAvY_uBKI/AAAAAAAACmY/npMufvUm0jksEnRNetG5Y-JIuOHIzh3cgCLcBGAs/s1600/20180430_164021-cut-color.jpg" imageanchor="1" style="margin-left: auto; margin-right: auto;"><img border="0" data-original-height="566" data-original-width="500" height="320" src="https://4.bp.blogspot.com/-QiRg2C90bhY/WufAvY_uBKI/AAAAAAAACmY/npMufvUm0jksEnRNetG5Y-JIuOHIzh3cgCLcBGAs/s320/20180430_164021-cut-color.jpg" width="282" /></a></td></tr>
<tr><td class="tr-caption" style="text-align: center;">Battery connector destroyed.</td></tr>
</tbody></table>
<br />
The lesson here is <i>either</i> that I am incapable of treating a piece of history with the required tenderness <i>or</i> that one should just leave good enough alone. Good enough? Well it turns out that the machine works perfectly fine with an empty battery. Better yet, it works perfectly fine even with a <i>ripped out</i> battery. So luckily I did not actually destroy the entire machine with this horrible mistake. If I ever decide to give my Qube 2 the "same" treatment, I'll desolder the entire battery socket instead and replace it with a less insane one.<br />
<br />
<i>To be continued... :-)</i>Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com1tag:blogger.com,1999:blog-2240283907729630332.post-17629071800821095752018-01-27T16:11:00.001+01:002018-01-27T16:16:26.704+01:00Unlock LUKS Remotely on Ubuntu 16.04 LTSI reinstalled my little server at work. It had been running the same <a href="https://www.gentoo.org/" target="_blank">Gentoo</a> setup since 2008 (!) but in December 2017 the <a href="https://www.gentoo.org/" target="_blank">Gentoo</a> folks finally managed to produce a convoluted enough update to completely hose the darn thing. Well, not "hose" as in "disaster" of course: I got all the data off safely and I could even leave it running over the holidays while I was away in Germany. But in preparation for the Spring 2018 semester it was necessary to "start from scratch" as it were.<br />
<br />
Upset enough with <a href="https://www.gentoo.org/" target="_blank">Gentoo</a> I decided to go <i>completely</i> the other way and do a minimal <a href="https://www.ubuntu.com/" target="_blank">Ubuntu</a> <a href="http://releases.ubuntu.com/16.04/" target="_blank">16.04 LTS</a> install. I also used this opportunity to finally add full-disk <a href="https://en.wikipedia.org/wiki/Linux_Unified_Key_Setup" target="_blank">LUKS</a> encryption to my setup. Not that it makes much sense (the server runs 24/7 so it's basically always decrypted) but what the heck, this is how you're supposed to set up your server, right? And instead of going for ZFS or btrfs (which is what I used on my new home machine), I went "retro" one last time:<br />
<br />
<ol>
<li>Partition the disks into one "small" boot partition and one "large" data partition.</li>
<li>Use mdadm to create a RAID-1 boot and a RAID-10 data array.</li>
<li>Use cryptsetup to LUKS-encrypt the "huge" data RAID array.</li>
<li>Use LVM to create swap, root, and various home volumes in the encrypted RAID.</li>
</ol>
<br />
Great! But now I had a problem. You see, every now and then we actually have a power outage. (I know it's weird, but since we're not the hospital we apparently don't get to have a redundant power grid.) I might not be around to reboot the machine manually, but students want to submit their homework assignments. And I don't like giving extensions. So what to do?<br />
<br />
Enter the recent <a href="https://packages.ubuntu.com/xenial/dropbear-initramfs" target="_blank">dropbear-initramfs</a> package! This thing is supposed to integrate a tiny <a href="https://matt.ucc.asn.au/dropbear/dropbear.html" target="_blank">dropbear</a> SSH server into the <a href="https://en.wikipedia.org/wiki/Initial_ramdisk" target="_blank">early root filesystem</a>, enabling "remote unlocking" of the encrypted RAID array. And it almost works. First the easy parts:<br />
<br />
<ol>
<li>apt install dropbear-initramfs (and ignore the error message)</li>
<li>mkdir -p /etc/initramfs-tools/root/.ssh/</li>
<li>Put your SSH keys into /etc/initramfs-tools/root/.ssh/authorized_keys</li>
<li>update-initramfs -u</li>
</ol>
<br />
Now when the machine boots up, it'll still ask for a passphrase on the console, but it will also start the dropbear SSH server. In theory you can ssh in as root at that point and run the unlock script, but that didn't work for me. What did work, however, is to echo the passphrase directly to the FIFO created by cryptsetup:<br />
<br />
<ol>
<li>ssh root@server</li>
<li>echo -n passphrase >/lib/cryptsetup/passfifo</li>
<li>exit</li>
</ol>
<br />
At this point the encrypted RAID will come up and the boot process will continue, just as if you had typed the passphrase at the console. I am <i>positive</i> that they'll eventually fix the scripts, but for now I am just happy that I was able to make it work.<br />
<br />
Note that it's convenient to run dropbear SSH and the regular OpenSSH on different ports to avoid getting loads of useless warnings when connecting. It's also just good sane practice if you want to keep the number of script kiddies trying to get into your server down to a minimum. Yes, <a href="https://en.wikipedia.org/wiki/Security_through_obscurity" target="_blank">security through obscurity</a> is bad, but it's only really bad if it's your only approach. Happy remote booting!Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com0tag:blogger.com,1999:blog-2240283907729630332.post-21707854606453225352017-10-13T06:42:00.000+02:002017-10-13T06:42:48.753+02:00Buying an Old ThinkpadI've recently been bitten by the <i>theoretical</i> <a href="https://en.wikipedia.org/wiki/ThinkPad" target="_blank">Thinkpad</a> bug. That is, I can see the attraction of these machines but I have no <i>practical</i> experience with them, especially not with the <a href="https://en.wikipedia.org/wiki/Pointing_stick" target="_blank">weird red dot</a> on their keyboards. I also <i>hate</i> my <a href="https://nilisnotnull.blogspot.com/2015/05/linux-on-lenovo-z585.html" target="_blank">current Lenovo laptop</a> with a passion, so spending a lot of money without knowing if I'll like the machine seemed ill-advised indeed.<br />
<br />
The good news is that the entire Thinkpad line seems to thrive on a myth of "eternal stability" meaning they simply don't change much (on the outside anyway) from year to year. So I figured I should just buy an older model for less money and see how it handles. If I end up liking it, I'll eventually shell out the dough for a new one.<br />
<br />
I am obviously not the first person with that idea. Here's a <a href="https://www.reddit.com/r/thinkpad/wiki/intro" target="_blank">reddit page</a> that explains why older Thinkpads are a great way to go and there's even a <a href="http://ktgee.net/post/49423737148/thinkpad-guide" target="_blank">buyer's guide</a> specifically targetting older machines. So this post is less about pitching the idea of older Thinkpads and more about my own deliberations on which old model to get.<br />
<br />
I decided to play the role of a "serious" user so the only Thinkpads I even considered were the <a href="https://en.wikipedia.org/wiki/ThinkPad_T_Series" target="_blank">T series</a> and the <a href="https://en.wikipedia.org/wiki/ThinkPad_X_Series" target="_blank">X series</a>. The strange sliver of my personality that made me an Apple fanboy back in the 1998-2004 time frame is <i>immensely</i> attracted to the X series. Thin, light, compact, sexy, wow! However, the newly discovered grown-up in me tends to prioritize things differently. I need a machine that I can work on comfortably for <i>hours at a time</i> which means I need a big display, good hand rests, a spacious keyboard, etc. If I <i>really</i> fall in love with Thinkpads during this experiment, no doubt I'll <i>eventually</i> own an X series product as well. But for now I'll stick to the T series.<br />
<br />
Within the modern T series we have the bigger T5xx models (15.6" display, numeric pad) as well as the smaller T4xx models (14" display, no numeric pad). This is sort of a toss-up for me: A larger display is nice, but a numeric pad is completely useless. In terms of weight we're looking at 4.5 to 6 pounds for T5xx machines versus 3 to 5 pounds for T4xx machines (across the 2008-2017 time frame that is).<br />
<br />
Just looking at the numbers above I couldn't really make up my mind until I remembered that my <a href="https://nilisnotnull.blogspot.com/2015/05/linux-on-lenovo-z585.html" target="_blank">current Lenovo laptop</a> is in the T5xx class when it comes to size and weight. And I have to admit that something a little lighter would be a lot nicer to carry around. So the entire T4xx line qualifies, but only the relatively recent T550, T560, or T570 models are light enough in the T5xx line. The crappy current laptop also helped me determine my "historical" cut-off point: I have a 2012 laptop now and I don't want to go earlier than that in terms of technology.<br />
<br />
So now I am left with the T430-T470 as well as the T550-T570 in terms of my various criteria. But wait, the whole point was to buy an <i>older, cheaper</i> Thinkpad! That narrows the field further to just three realistic categories:<br />
<br />
<ul>
<li>2012: T430, T430s, T430u</li>
<li>2013: T431s, T440, T440s, T440p</li>
<li>2015: T450, T450s, T550</li>
</ul>
<br />
So I started looking into all these models and the first thing I noticed was that the T431s and all the T440 models have a <a href="https://www.reddit.com/r/thinkpad/comments/2g81qu/lenovo_admits_new_trackpad_was_a_mistake_idf_14/" target="_blank"><i>very</i> different trackpad setup</a> from the rest (and indeed from all Thinkpads before and since). That takes all of these machines out of the race as well, after all I want to have a "true Thinkpad experience" and not some strange aberration that only existed for a brief instant.<br />
<br />
For the remaining models, I decided to read all the in-depth reviews I could find. But after doing that for a while, I realized that there's really only <a href="https://www.notebookcheck.com/" target="_blank"><i>one</i> review site</a> worth reading, so here are the links to all those reviews, followed by my own comments:<br />
<br />
<ul>
<li><a href="https://www.notebookcheck.net/Review-Lenovo-ThinkPad-T430-Notebook.81802.0.html" target="_blank">T430</a>: The i7 tends to run hot at 55C. Granted, only under load, but I don't like the idea of a runaway computation setting my couch on fire. So it's out.</li>
<li>T430s: The <a href="https://www.notebookcheck.net/Review-Lenovo-ThinkPad-T430s-Notebook.82261.0.html" target="_blank">i5/620M</a> tends to run warm at 43C, the <a href="https://www.notebookcheck.net/Review-Update-Lenovo-ThinkPad-T430s-Notebook.83532.0.html" target="_blank">i7/4000</a> tends to run warm at 46C, neither of which is terrible. Despite being smaller and lighter than the T430 this thing still has an optical drive bay, something I like. Depending on condition and features, these ran between $170 (crappy) and $400 (like new).</li>
<li><a href="https://www.notebookcheck.net/Review-Lenovo-ThinkPad-T430u-Ultrabook.86977.0.html" target="_blank">T430u</a>: The i5 tends to run warm at 45C. It's the only older model with HDMI, a big plus in retrospect. However, it's also the one model with <i>only</i> a fixed battery and that's a big minus. But worst of all the screen is <i>terrible</i>, so it's out.</li>
<li><a href="https://www.notebookcheck.net/Lenovo-ThinkPad-T450-Ultrabook-Review.139988.0.html" target="_blank">T450</a>: The i5 tends to run warm at 47C and I'd be okay with that. What I wasn't okay with is that these started at $520 which I deemed too expensive.</li>
<li>T450s: The <a href="https://www.notebookcheck.net/Lenovo-ThinkPad-T450s-Ultrabook-Review.137248.0.html" target="_blank">i7/5500</a> is a dream and runs cool at 36C even under load! The <a href="https://www.notebookcheck.net/Lenovo-ThinkPad-T450s-Ultrabook-Review.142700.0.html" target="_blank">i5/940M</a> on the other hand runs hot at 52C which is too much for me. Alas it didn't matter, also too expensive at $600+.</li>
<li><a href="https://www.notebookcheck.net/Lenovo-ThinkPad-T550-Notebook-Review.137974.0.html" target="_blank">T550</a>: The i7 tends to run cool at 39C. Sadly most of these were also <i>very</i> expensive ($750+), the only affordable one I could find (at $379) had a <i>locked BIOS</i>.</li>
</ul>
<br />
I am obviously a little obsessed with temperatures. Everybody has their thing and I've had plenty of "laptop too hot for my lap" experiences that I don't care to repeat.<br />
<br />
You can probably guess that I finally settled on the T430s for my experiment. The one I ordered was a <i>little</i> more expensive than I had hoped for ($265 instead of $250) but that's close enough. What convinced me in the end was that the seller actually wrote a long reply, covering all the details that were important to me.<br />
<br />
Once it gets in, I'll try to do another post (maybe with pictures) about the machine and then it's on to actually testing it by replacing my current laptop for a week or three of lectures. Oh, and I need to order an <a href="https://www.monoprice.com/product?c_id=104&cp_id=10428&cs_id=1042802&p_id=12742&seq=1&format=2" target="_blank">HDMI adapter</a> because we mostly have HDMI at Johns Hopkins these days.Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com4tag:blogger.com,1999:blog-2240283907729630332.post-67573604960851909382017-10-13T06:10:00.000+02:002017-10-13T06:10:41.539+02:00Playing id Classics on LinuxJust for reference since I've been going through a somewhat extreme retro-gaming phase lately. Of course you'll need the actual game data for all of these. Luckily I have old CD-ROMs that still work fine (even though I of course have backups as well). The details for extracting the data vary, maybe that's a topic for a future post. But if you can extract it, here's what to run the games with:<br />
<br />
<ul>
<li><b>DOOM, DOOM 2, ...</b>: For the best "retro-feeling" I recommend <a href="https://www.chocolate-doom.org/" target="_blank">Chocolate Doom</a>. If your distro doesn't package it, just <a href="https://github.com/chocolate-doom/chocolate-doom" target="_blank">grab the source</a> and build it yourself, it's not hard. Youngsters may not like it because it's designed to give you an "accurate" 1993 experience (pixels!), but that's how it's meant to be played so deal with it.</li>
<li><b>Quake, ...</b>: The only thing I <i>can</i> recommend is the <a href="https://icculus.org/twilight/darkplaces/" target="_blank">DarkPlaces</a> engine. Don't get me wrong, it's an awesome effort and it does indeed look a lot better than the original. But my vintage 2009 graphics card actually has trouble keeping up which is a little sad for what is ostensibly a 1996 game. Alas, every other source port I tried didn't actually work, so... Also surprisingly easy to build, just <a href="https://icculus.org/twilight/darkplaces/download.html" target="_blank">grab the source</a> and hit make. Just be prepared to wait a little longer than for the Chocolate Doom build.</li>
<li><b>Quake 2, ...</b>: Even fewer choices for Quake 2, but luckily <a href="https://www.yamagi.org/quake2/" target="_blank">Yamagi Quake 2</a> is excellent and they didn't overdo it with the graphical polish. I can play this at full speed with all the options turned up and it looks more or less like it should. Once again a pretty easy build, just <a href="https://github.com/yquake2/yquake2" target="_blank">grab the source</a> and boom there it is. One minor quibble: They don't have a command line flag to configure the base path, so if you don't want to throw the executable into your data partition you'll have to change two lines in the Makefile.</li>
</ul>
<br />
There you have it, the stuff I've been playing with over the last two weeks or so. Good clean retro fragging, who can resist? I may update this post with more details if there's interest, so leave a comment if you prefer another engine that I missed or if you can't get the above to work for you.Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com0tag:blogger.com,1999:blog-2240283907729630332.post-30911643604740287962017-07-23T07:07:00.000+02:002017-07-23T07:07:42.528+02:00Protecting Weaker Party MembersI am currently running a B/X game that started with the sentence "<i>We've all decided to play magic-users!</i>" from one of the players. Luckily <a href="https://gorgonmilk.blogspot.com/2013/02/ability-score-rolling-matrix.html?showComment=1451340075504#c3859990299641657294" target="_blank">my adopted variant</a> of "3d6 in order" prevented that outcome and they're a pretty typical "murderhobo" party now: two magic-users, two fighters, one thief, and one blood-thirsty halfling with suspenders but no shirt. (There <i>was</i> a cleric, but that's another story.)<br />
<br />
In any case, one of the players was "completely new" and of course I recommended that she play a fighter. I sold this mostly with "it's the easiest class to run" but also with "all those robes-and-silly-hats people will need protection" which is what me got thinking:<br />
<br />
<blockquote class="tr_bq">
<i>There is no "rule" in B/X that would allow a fighter to protect a magic-user or anyone else for that matter.</i></blockquote>
<br />
Seemed like something important to offer at the time, but looking around the many B/X house rule documents out there I couldn't find the problem addressed by anyone. Even <a href="https://deltasdnd.blogspot.com/" target="_blank">Delta</a> who has probably forgotten more D&D than I will ever know left me out in the cold on this topic (aside from mentioning the need to have <a href="https://deltasdnd.blogspot.com/2011/12/friday-night-book-of-war.html" target="_blank">lots of fighters to protect magic-users</a> in mass battles).<br />
<br />
I wanted a simple mechanic that would make the protected character "safer" in some way (benefit) while also "exposing" the protecting fighter more (cost). I quickly settled on two "ground rules" for this:<br />
<br />
<ul>
<li>The fighter must be "close" (within 5' say) to the character they protect.</li>
<li>The fighter must be "aware" of an attack in order to protect against it.</li>
</ul>
<br />
I guess you could say that I am treating the fighter as an "intelligent shield" of sorts? That approach seems fair to me because I don't want a fighter to simply throw themselves over the character they are trying to protect. I very much want "protect<i>or</i>" and "protect<i>ee</i>" to still be "in combat" instead of changing the focus to a Secret-Service-style "Get him out of here!" and nothing else.<br />
<br />
The simplest thing I could come up with was to simply let the fighter take the damage. So as a rule, I'd phrase it something like this:<br />
<br />
<blockquote class="tr_bq">
<i>Fighters can choose to protect one character within 5' of them. If the protected character gets hit by an attack the fighter is aware of, the fighter can choose to take the damage instead.</i></blockquote>
<br />
Not too shabby in terms of simplicity, is it? But as always the "devil" is in the details. First of all this conveys almost complete immunity to the protected character. But the goal was to make them "safer" only, not "safe". In other words, I still want the magic-user to worry about maybe having their spell interrupted. Also we have reduced the fighter to an <i>actual</i> meat shield ("bag of hit points") and <i>nothing</i> else: Regardless of how good their AC is, they now get skewered because of the (presumably) much worse magic-user AC. That's not fun at all for whoever is playing the fighter. Finally, if we have multiple fighters protecting one character, the "immunity" could actually be complete and it could go on for a long time indeed. This may work great for Delta's mass combat scenario, but on the "party in a dungeon" scale I wouldn't want to deal with it.<br />
<br />
<br />
So instead of letting the fighter take all the damage, let's try to do something about getting hit in the first place. Here's what I came up with next:<br />
<br />
<blockquote class="tr_bq">
<i>Fighters can choose to protect one character within 5' of them. Attacks against the protected character that the fighter is aware of suffer a -8 penalty. Attacks against the fighter, however, gain a +2 bonus.</i></blockquote>
<br />
The numbers are subject to debate of course, but this seemed fair to me. Presumably the kobold archers trying to hit the magic-user would notice that the fighter brushed away all their arrows, so next round they'd redirect their fire. But as so often when you design a rule with fixed penalties/bonuses, there's an exploit: Two or more fighters <i>protecting each other</i> would impose a -6 penalty against most attacks, clearly not the application that was intended. Except for that terrible flaw, however, we would get the desired effects: The protected character still has to worry about getting hit, and the fighter now makes for an easier target because they are "out there" trying to distract attackers.<br />
<br />
What finally made me think of a better solution is this: With the fixed penalty, a <i>naked</i> fighter could protect a character in plate and shield. That makes no sense! What should happen instead is something like this:<br />
<br />
<blockquote class="tr_bq">
<i>Fighters can choose to protect one character within 5' of them. Attacks against the protected character that the fighter is aware of must hit the fighter's armor class instead (provided that armor class is better). Any damage is still suffered by the protected character. Attacks against the fighter also gain a +2 bonus.</i></blockquote>
<br />
I am reasonably happy with this rule. It's a little more complex, but not overly so. It does allow protecting weaker party members if they have a worse armor class, but it doesn't make them (almost) completely safe. It also has no obvious exploit that I can think of, mostly by virtue of letting the better armor class prevail. I'd also say that a spell like <i>Protection from Normal Missiles</i> cannot be used with this rule as it doesn't affect armor class, but your mileage may vary.<br />
<br />
I've added the last version as a house rule to said B/X game, but after two sessions so far it has not seen any use yet. Admittedly the characters were not really in situations where it made much sense to try yet, but here's to hoping someone will attempt it sometime soon. In the meantime, I'd love to hear what everybody out there thinks of what I did here.<br />
<br />
BTW, I <i>am</i> aware of the 5th edition <a href="http://www.brandesstoddard.com/2016/03/dd-5e-the-protection-fighting-style/" target="_blank">Protection Fighting Style</a> thing but it's just too horribly complicated and too far from B/X to try to convert. It's interesting however that the 5e folks also thought that the "big fighter protecting small magic-user" trope needed "a bit more rule" behind it.Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com10tag:blogger.com,1999:blog-2240283907729630332.post-2394244916041231082016-12-29T15:52:00.000+01:002016-12-29T18:07:54.133+01:00Editions of Armor Class Part 1: No ArmorA few weeks ago one of <a href="http://zenopusarchives.blogspot.de/2016/12/gygaxian-armor.html" target="_blank">Zenopus' excellent posts</a> made me think about "armor class" in D&D again. On <a href="https://plus.google.com/103373466658249785171/posts/Yun8a95Botc" target="_blank">Google+</a> I even commented "<i>I like that booklet too, but I really couldn't care less about AD&D armor classes. The original system just makes so much more sense. I feel a blog post coming on...</i>" Sadly life happened and I couldn't find the time to write about the crazy in my head then. But now that I am safely tucked away in Germany for my year-end vacation, I figured I'd give it a quick shot.<br />
<br />
<b>Disclaimer:</b> In true grognard-style I shall only consider "descending armor class" in the following. I don't care about "ascending armor class" systems, especially since the usual "selling point" of those doesn't apply once you use <a href="http://deltasdnd.blogspot.de/2009/07/what-is-best-combat-algorithm.html" target="_blank">Delta's Target20 mechanic</a>.<br />
<br />
Let's begin with the classic AC 9 versus AC 10 debate: Should an <b>average</b> character who is <b>not</b> wearing any armor be AC 9 as OD&D, B/X, and BECMI profess, or AC 10 as AD&D wants us to believe? For me, any answer that doesn't immediately consult the combat tables is of a purely religious nature. It really doesn't matter whether we start at AC 9 or AC 10, what matters is whether there's a difference in running a combat. Here I prefer the B/X (and to some extent BECMI) story:<br />
<br />
<blockquote class="tr_bq">
<i>Two average, unarmored, untrained, "normal humans" should have a 50% chance per round to hit (and most likely kill) each other.</i></blockquote>
<br />
I don't know about you, but that seems perfectly reasonable to me. It certainly shouldn't be more than 50% because that would imply skill where (by definition) none should exist. And if it was less than 50% things would just drag out longer.<br />
<br />
If you consult the B/X Basic Set, page B27, you'll see that a "normal man" indeed needs an 11+ to hit AC 9, a chance of 50% on a d20 roll. Perfect! As for the "most likely kill" part: On page B25 we find that a successful attack does 1-6 points of damage (average 3.5) while page B40 explains that "normal humans" have 1-4 hit points (average 2.5). Death incarnate!<br />
<br />
In the BECMI Expert Set (but not the Basic Set, go figure!) we find the same "11+ to hit AC 9" for "normal man" on page 29; alas the BECMI Basic Set says that "normal humans" have 1-8 hit points (average 4.5) so things are a little less deadly (never mind the other problems this change causes, sigh).<br />
<br />
What about OD&D? On page 19 of "Men and Magic" we find (perhaps surprisingly?) that "normal men equal 1st level fighters" which means they only need a 10+ to hit AC 9, a chance of 55% on a d20 roll. Granted, it's only a 5% difference, but that seems wrong to me. Why would an untrained combatant have the same skill as a trained one?<br />
<br />
AD&D does away with "normal men" for the most part, replacing it with the notion of "0 level" characters (for which only humans and halflings qualify?). AD&D also recalibrates to AC 10 for "no armor" of course. Well, at least starting in the Player's Handbook it does, the <a href="http://zenopusarchives.blogspot.de/2012/08/the-monster-manual-is-holmes-supplement.html" target="_blank">Monster Manual seems to be</a> written to the <a href="http://zenopusarchives.blogspot.de/2016/12/gygaxian-armor.html" target="_blank">original AC 9 for "no armor"</a> instead. But at least Gary manages to stay somewhat true to my B/X story: On page 74 of the Dungeon Master's Guide we learn that "0 level" characters need 11+ to hit AC 10, a chance of 50% on a d20 roll again. Of course average hit points are "off" as in BECMI, see page 88 of the Dungeon Master's Guide.<br />
<br />
So then... What should "no armor" be, AC 9 or AC 10? As I said before, it doesn't matter! B/X (and to a lesser degree BECMI and even AD&D) get it "right" as far as I am concerned, only OD&D has it "wrong" since it doesn't distinguish trained from untrained combatants.<br />
<br />
Of course there is <b>one</b> difference after all: I strongly prefer single-digit AC values, and so in the final analysis, AD&D is out. But I have to admit that this preference is mostly "religious" as well, not truly "technical" as it were. True, <a href="http://deltasdnd.blogspot.de/2009/07/what-is-best-combat-algorithm.html" target="_blank">Target20</a> is easier with single-digit AC values, but since that's not a standard mechanic I can't really use it to "rationalize my irrationality" too much. Does "neater table layout with single digits" count?Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com1tag:blogger.com,1999:blog-2240283907729630332.post-10320721785698868252016-10-14T20:03:00.000+02:002016-10-14T20:03:07.926+02:00The S.M.A.R.T. OverflowBefore today, I didn't realize that <a href="https://en.wikipedia.org/wiki/S.M.A.R.T.">S.M.A.R.T.</a> has overflow issues. I should say that I spent most of yesterday replacing three disks in my home machine's <a href="https://en.wikipedia.org/wiki/Nested_RAID_levels#RAID_10_.28RAID_1.2B0.29">RAID-10</a>, so I constantly was using <a href="https://www.smartmontools.org/">smartctl</a> to double-check stuff. So when I got to work today, I poked around the disks in my server. And I noticed this:<br />
<br />
<blockquote class="tr_bq">
<span style="font-family: "Courier New",Courier,monospace;">...</span><br />
<span style="font-family: "Courier New",Courier,monospace;">SMART Self-test log structure revision number 1<br />Num Test_Description ... LifeTime(hours) ...<br /># 1 Short offline ... 2484 ...</span><span style="font-family: "Courier New",Courier,monospace;"><br /># 2 Short offline ... 2469 ...<br /># 3 Short offline ... 2445 ...<br />...</span></blockquote>
<br />
This made absolutely no sense, because I <i>knew</i> that most of the disks in there were <i>certainly</i> older than a few months. After some digging, I came to realize what the problem is:<br />
<br />
<blockquote class="tr_bq">
<span style="font-family: "Courier New",Courier,monospace;">...</span><br />
<span style="font-family: "Courier New",Courier,monospace;">SMART Self-test log structure revision number 1<br />Num Test_Description ... LifeTime(hours) ...<br /># 1 Short offline ... 1276 ...<br /># 2 Short offline ... 62136 ...<br /># 3 Short offline ... 61776 ...</span><br />
<span style="font-family: "Courier New",Courier,monospace;">...</span></blockquote>
<br />
The actual value for <span style="font-family: "Courier New",Courier,monospace;">Power_On_Hours</span> is 66812 for that disk. Let's subtract 1276 from that and what do we find? <span class="cwcot" id="cwos">65536 of course. So the life time recorded with each self-test is apparently an unsigned 16-bit value, whereas the total hours recorded for the disk itself is stored as something bigger. Here's to hoping that people who write scripts telling them which disks to swap are aware of this...</span>Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com0tag:blogger.com,1999:blog-2240283907729630332.post-30410048477039298002016-06-30T03:01:00.000+02:002016-06-30T03:01:31.052+02:00Choice of Class: Enforce or Encourage?For as long as I can remember, I've been a fan of "minimum ability score"-type requirements for classes. See, for example, my "addendum" at the bottom of <a href="http://nilisnotnull.blogspot.com/2014/12/the-strict-reading-of-spell-books-in-bx.html">this post</a> or, more recently, <a href="http://nilisnotnull.blogspot.com/2015/12/ability-score-minimums-in-bx-part-1.html">these</a> <a href="http://nilisnotnull.blogspot.com/2015/12/ability-score-minimums-in-bx-part-2.html">posts</a>.<br />
<br />
It just made sense to me that fighters should have (at least) average strength and that wizards should have (at least) average intelligence. In case of the wizard, I still think it makes perfect sense even from an "in game" perspective: Why would that archmage waste his or her time training a moron? In case of the fighter, well, maybe strength is not so important: After all, one purpose of having many soldiers (whether weak or strong) on the field is just so that more can die before whatever lord commands them actually loses a battle. (The term "<a href="https://en.wikipedia.org/wiki/Cannon_fodder">cannon fodder</a>" exists for a reason.)<br />
<br />
But more importantly, I just couldn't see why anyone would want to play a weak fighter or a dumb wizard. So the idea of using "minimum scores" to control what classes a player can pick seemed perfectly alright, even if it meant that there would be a small percentage of characters who can't qualify for any class at all: Just re-roll those, problem solved.<br />
<br />
However, it recently dawned on me that I don't speak for everybody. (Shocker!) What if there is a player who <i>does</i> enjoy that weak fighter? Maybe that fighter, while physically not "up to snuff" as it were (low strength), is a master strategist and leader (high intelligence and charisma)? True, the player could choose a wizard instead, but that would make for a very different type of leader, maybe not what they were going for.<br />
<br />
(Things get worse if you allow players to <a href="http://nilisnotnull.blogspot.com/2014/12/mixing-and-matching-classes.html">multi-class</a>. Now the ability scores would have to be good enough for <i>two</i> classes, something that's not particularly likely with 3d6 even if the minimum requirements are low-ish.)<br />
<br />
Instead of <i>enforcing</i> the set of classes that a given character can choose from, it may be preferable to <i>encourage</i> certain choices (and to <i>discourage</i> others of course). The "good news" is that we already have a mechanic that does just that, and it has existed in all relevant versions of D&D since 1974: <i>Experience point adjustments for prime requisites.</i> Here's what the B/X rules say:<i><br /></i><br />
<br />
<blockquote class="tr_bq">
<i>The ability most important to a class is called the <b>prime requisite</b> for that class. The higher the prime requisite score, the more successful that character will be in that class.</i><br />
<div style="text-align: right;">
Basic Rulebook, Page B6</div>
</blockquote>
<br />
The details are not horribly important, and you probably know them anyway, so let's just summarize that the score in a prime requisite results in a bonus (or penalty) of up to +10% (or -20%) on the experience points earned by the character. Now I should first point out that I used to <i>hate</i> these adjustments. The math is not too horribly bad, but we're still left with a bag of questions:<br />
<br />
<ul>
<li>Exactly what ability score counts for the experience adjustment? The initial score when the character was created? The current score which might be adjusted by a magic item or a curse?</li>
<li>Does a change in a prime requisite ability score retroactively affect the current experience point total? If so, raw experience points and bonus experience points should be tracked separately.</li>
<li>What is the "in game" justification for the bonus (or penalty) on experience points? The D&D experience system is already on pretty weak grounds (exactly how does getting richer make someone better at picking locks again?) and it seems these adjustments make even less sense in that light.</li>
</ul>
<br />
Note, however, that minimum ability score requirements actually raise many of the same questions: If you're a fighter with strength 9 but get cursed to have strength 6, are you still a fighter? If you rolled a character with strength 4 but the DM grants you Gauntlets of Ogre Power at character creation, can you pick the fighter class? And what happens when you lose those gauntlets? Also, regardless of whether we consider XP = GP good or bad, that's still the default in old-school D&D, so why worry when the system gets a little more insane? It's already nuts but most people don't really mind.<br />
<br />
What I came away with after thinking about this for the past week or so was mildly surprising to me:<br />
<br />
<blockquote class="tr_bq">
After 20+ years of <i>disliking</i> the prime requisite experience adjustment rule, I now think it's a <i>stroke of genius</i>!</blockquote>
<br />
It allows the player to make more choices for his or her character, and that's never a bad thing (well, almost never, let's hope newbies will have a supportive DM to cut down the number of choices a little). It encourages certain choices, but it doesn't force anything. In fact, coming up with a background that explains why that dunce with intelligence 6 was able to get training as a wizard actually sounds like a lot of fun.<br />
<br />
In my particular house rules, things get even better. Say someone wants to multi-class as a fighter/priest to approximate a paladin-like character. If they have average strength and wisdom, they simply progress on the slower XP table for characters with two classes. If they have excellent strength and wisdom for a +10% bonus on XP each, they actually progress with +20% on that harder/slower table. If they are weak (-10% penalty due to low strength) but pretty wise (+10% bonus due to high wisdom) things cancel out: It's still a viable paladin-like character.<br />
<br />
So I am off to rewriting my house rules yet again: <b>No more minimum ability score requirements for classes!</b> (Hmm, should I add some for races now?)<br />
Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com0tag:blogger.com,1999:blog-2240283907729630332.post-55346248446165700572016-04-22T18:23:00.000+02:002016-04-22T18:23:35.724+02:00Tracking Positions in Go: Why Composition RocksIn this post I discuss the genesis of the <a href="https://godoc.org/github.com/phf/streampos">streampos</a> package for <a href="https://golang.org/">Go</a> that I recently posted on <a href="https://github.com/phf/streampos">github</a>. I don't normally write about code I post, but in this case I learned something cute that I wanted to share. Maybe you'll find it enjoyable too?<br />
<br />
The story starts with me writing some Go code to process XML files. Of course I used the <a href="https://golang.org/pkg/encoding/xml/">encoding/xml</a> package from the Go standard library to do this. A few hours into the job I needed to generate error messages when something is not quite right in the XML file. (If you've dealt with large-ish XML files that get edited manually, you probably know that it's quite easy to make the occassional mistake that syntax highlighting alone will not protect you from.) In order for those error messages to be useful, they should tell the user <i>where</i> in the XML file the problem was detected. And that's when I ran into trouble: There's <i>no straightforward way</i> to get, say, line numbers out of <a href="https://golang.org/pkg/encoding/xml/">encoding/xml</a>!<br />
<br />
Sure, <i>their</i> code tracks line numbers in support of <i>their</i> error messages (check <br />
<a href="https://golang.org/pkg/encoding/xml/#SyntaxError">SyntaxError</a> for example) but if you have <i>your own errors</i> that go beyond what the standard library checks, you're out of luck. Well, not <i>completely</i> out of luck. If you're using <a href="https://golang.org/pkg/encoding/xml/#Decoder">Decoder</a> to do stream-based XML processing, you <i>can</i> get something moderately useful: the <a href="https://golang.org/pkg/encoding/xml/#Decoder.InputOffset">InputOffset</a> method will give you the <i>current offset</i> in <i>bytes</i> since the beginning of the stream.<br />
<br />
What do you have to do to turn <i>that</i> into error messages of the kind users expect, so error messages in terms of line (and maybe column) numbers? First you somehow have to get your hands on the raw input stream. Then you look for newlines and build a data structure that allows you to map a range of offsets in the stream into a line number. With a little more code on top, you even get out column numbers if you want them. Sounds like fun, but just how should we do it?<br />
<br />To use <a href="https://golang.org/pkg/encoding/xml/#Decoder">Decoder</a> you have to give it a <a href="https://golang.org/pkg/io/#Reader">Reader</a> to grab input from. This is promising because Go very much prides itself in the power that simple interfaces like <a href="https://golang.org/pkg/io/#Reader">Reader</a> and <a href="https://golang.org/pkg/io/#Writer">Writer</a> provide. Indeed, the pattern of wrapping one Reader inside another (or one Writer inside another) is fundamental in much of the standard I/O library. But we can also find those interfaces in "unrelated" parts of the library: The <a href="https://golang.org/pkg/hash/#Hash">Hash</a> interface, for example, is a Writer that computes hashes over the data written to it.<br />
<br />
So the Decoder wants a Reader, but thanks to interfaces <i>any</i> Reader will do. It's not a big leap to think "<i>Hey, I can hack my own Reader that tracks line numbers, and I'll pass that one to Decoder instead of the original Reader!</i>" That's indeed what I considered doing for a few minutes. Luckily I then realized that by hacking a <i>Reader</i> I am actually making myself <i>more problems</i> than I had to begin with.<br />
<br />
I want to solve the problem of building a mapping from offsets to line numbers. However, as a Reader, I <i>also</i> have to solve the problem of providing data to whoever is calling me. So whatever the original problem was, as soon as I decide to solve it inside a Reader, I immediately get a second problem. And it's not an entirely trivial problem either! For example, I have to consider what the code should do when asked to provide 37 bytes of data but the underlying Reader I am wrapping only gave me 25. (The answer, at least in Go land, is to return the short read. But notice that it's something I had to <i>think about</i> for a little while, so it cost me time.) On a more philosophical level, inserting a Reader makes my code an integral part of the entire XML thing. I never set out to do that! I just wanted a way to collect position information "on the side" without getting in anybody's way.<br />
<br />
In the specific case of <a href="https://golang.org/pkg/encoding/xml/">encoding/xml</a> things actually get even funnier. It turns out that <a href="https://golang.org/pkg/encoding/xml/#Decoder">Decoder </a>checks whether the <a href="https://golang.org/pkg/io/#Reader">Reader</a> we hand it is actually a <a href="https://golang.org/pkg/io/#ByteReader">ByteReader</a>. If it's not, Decoder chooses to wrap the Reader we hand it again, this time in a <a href="https://golang.org/pkg/bufio/#Reader">bufio.Reader</a>. So either I have to implement a ByteReader myself, or I have to live with the fact that plugging in my own Reader causes another level on indirection to be added, unnecessarily to some extent. (That's yet <i>another</i> problem I don't want to have to deal with!) There really should be a better way.<br />
<br />
And there is: Instead of hacking a Reader, just hack a <a href="https://golang.org/pkg/io/#Writer">Writer</a>! I can almost see you shaking your head at this point. "<i>If the Decoder wants a Reader, what good is it going to do you to hack a Writer?</i>" I'll get to that in a second, first let's focus on what being a Writer instead of a Reader buys us.<br />
<br />
The most important thing is that as a Writer, we can decide to be "the sink" where data disappears. That is, after all, exactly what the <a href="https://golang.org/pkg/hash/#Hash">Hash</a> interface does: It's a Writer that turns a stream into a hash value and nothing else, the stream itself disappears in the process. What's good enough for Hash is good enough for us: We can be a Writer that turns a stream into a data structure that maps offsets to line numbers. Note that a Reader doesn't have this luxury. Not ever. True, there could be Readers that are "the source" where data appears out of thin air, but there are no (sensible) Readers that can be "the sink" as described above.<br />
<br />
A secondary effect of "being the sink" is that we don't have to worry about dealing with an "underlying Writer" that we wrap. (As a Reader, we'd have to deal with "both ends" as it were, at least in our scenario.) Also, just like in the case of Hash, any write we deal with cannot actually fail. (Except of course for things like running out of memory, but to a large degree those memory issues are something Go doesn't let us worry about in detail anyway.) This "no failures" property will actually come in handy.<br />
<br />
Okay, so those are all nice things that will make our code simpler as long as we hack a <a href="https://golang.org/pkg/io/#Writer">Writer</a> and not a <a href="https://golang.org/pkg/io/#Reader">Reader</a>. But how the <i>heck</i> are we going to make our Writer "play nice" with the <a href="https://golang.org/pkg/encoding/xml/#Decoder">Decoder</a> that after all <i>requires</i> a Reader? Enter a glorious little thing called <a href="https://golang.org/pkg/io/#TeeReader">TeeReader</a>. (No, not TeaReader!) A TeeReader takes two arguments, a Reader r and a Writer w, and returns another Reader t. When we read from t, that request is forwarded to r. But before the data from r gets returned through t, it's also <i>written</i> to w. Problem solved:<br />
<br />
<blockquote class="tr_bq" style="font-family: "Courier New",Courier,monospace;">
lines := &streampos.Writer{}<br />
tee := io.TeeReader(os.Stdin, lines)<br />
dec := xml.NewDecoder(tee)</blockquote>
<br />
There's just one small problem with TeeReader: If the write we're doing "on the side" fails, that write error turns into a <i>read error</i> for the client of TeeReader. Of course that client doesn't really know that there's a writer involved anywhere, so things could get confusing. Luckily, as I pointed out above, our Writer for position information <i>never</i> fails, so we cannot <i>possibly</i> generate additional errors for the client.<br />
<br />
I could end the post here. But I don't want to sweep under the rug that there's a little cheating going on. Where? Well, you see, TeeReader is not a <a href="https://golang.org/pkg/io/#ByteReader">ByteReader</a> either. So regardless of how nice the code in our Writer is, and regardless of how cute the setup above is, we incur the cost of an extra indirection when <a href="https://golang.org/pkg/encoding/xml/#NewDecoder">NewDecoder</a> decides to wrap the TeeReader. What we're doing is shoving the problem back to the standard library. It's <i>possible</i> that TeeReader will eventually grow a ReadByte method at which point the needless wrapping would cease. However, that's <i>not very likely</i> given what TeeReader is designed to do. But note that this concern arises specifically in connection with <a href="https://golang.org/pkg/encoding/xml/">encoding/xml</a>. There are probably many applications that do not require methods beyond the <a href="https://golang.org/pkg/io/#Reader">Reader</a> interface.<br />
<br />
Speaking of other applications. In the Go ecosystem, interfaces such as Reader and Writer are extremely prominent. Lots of people write their code to take advantage of them. The nice thing is that <a href="https://godoc.org/github.com/phf/streampos#Writer">streampos.Writer</a> coupled with TeeReader provides a <i>generic</i> way to handle position information for <i>all</i> applications that use a Reader to grab textual data. Of course not all applications do, and not all applications will be able to take full advantage of it. But if you're writing one that does, and if you want to have position information for error messages, well, it's three lines of code as long as you already track offsets. And you <i>have to track something</i> yourself because after all only your application knows what parts of a stream are interesting.<br />
<br />
I very much like that Go encourages this kind of reusability by composing small-ish, independently developed pieces. (Actually, that even confirms a few of the claims I made in my 2003 dissertation. Yay me!) The only "trouble" is that there are already a few places in the standard library where similar position tracking code exists: At the very least in <a href="https://golang.org/pkg/text/scanner/">text/scanner</a> and in the Go <a href="https://golang.org/pkg/go/token/#Pos">compiler</a> <a href="https://golang.org/pkg/go/token/#Position">itself</a>. Whether that code could use my little library I don't know for sure, maybe not. But I guess it should be a goal of the standard library to refactor itself on occasion. We'll see if it does...<br />
<br />
One last note: I've been teaching a course on compilers since 2001, and since about 2003 I've told students to use byte offsets as their model of positions. I've always sold this by explaining that offsets can be turned into lines and columns later but we don't have to worry about those details in the basic compiler. Strangely enough I never actually wrote the code to perform that transformation, until now that is. So once I teach the course mostly in Go, I can use my own little library. Neat. :-)Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com0tag:blogger.com,1999:blog-2240283907729630332.post-50895240148397006732016-04-20T02:11:00.001+02:002016-04-24T00:13:49.641+02:00Terminal Multiplexers: Simplified and UnifiedI have a love-hate relationship with terminal multiplexers. I've been using <a href="https://www.gnu.org/software/screen/">screen</a> for years, but mostly on remote servers, and mostly just to keep something running on logout and later get back to it again. But on my home machine or my laptop, I've avoided terminal multiplexers like the <i>plague</i>, mostly because of their strange (or is "horrid" more appropriate?) user interfaces.<br />
<br />
For a really long time now, I've simply used <a href="http://wiki.lxde.org/en/LXTerminal">LXTerminal</a> and its tabs as a crutch, but I've recently grown rather tired of that approach. When you're writing (more or less complicated) client/server software, it really pays off to have both ends running side-by-side: switching tabs, even with a quick key combination, gets old fast. Also <a href="http://wiki.lxde.org/en/LXTerminal">LXTerminal</a> lacks quite a few features, true-color among them. What I really wanted to use was <a href="http://st.suckless.org/">st</a>, but that lean beast doesn't even have a scrollback buffer (so forget about tabs or a contextual menu).<br />
<br />
Wait, so why don't I just use a tiling window manager like <a href="http://dwm.suckless.org/">dwm</a> and open several terminals? Sadly I've been a spoiled <a href="http://openbox.org/wiki/Main_Page">Openbox</a> person since 2008 and a spoiled "overlapping windows" person since 1987 or so (thank the <a href="https://en.wikipedia.org/wiki/Amiga">Amiga</a> for that). I like the idea of a tiling window manager exactly for a bunch of terminals and not much else. In the long run I may actually become a <a href="http://dwm.suckless.org/">dwm</a> nut, but not just yet.<br />
<br />
So I had to face it, the time was right to <i>actually</i> learn a terminal multiplexer <i>for real</i>. But which one? For text editors there's an easy (if controversial) answer: just learn <a href="https://en.wikipedia.org/wiki/Vim_(text_editor)">vi</a> or <a href="https://www.gnu.org/software/emacs/">emacs</a>, both of those you're likely to find on any UNIX system you may ever have to work with. (Heck even <a href="https://www.busybox.net/">busybox</a> has a <a href="https://git.busybox.net/busybox/tree/editors/vi.c">vi</a> clone.) That seems to suggest that I should spend time on learning <a href="https://www.gnu.org/software/screen/">screen</a> for real: It's the oldest terminal multiplexer out there, so it's most likely to be available just about everywhere.<br />
<br />
The only problem is that it sucks. If you want to see why it sucks, just start <a href="http://hisham.hm/htop/">htop</a> in <a href="https://www.gnu.org/software/screen/">screen</a>. I don't care if that's a terminfo problem or not, in <a href="https://www.gnu.org/software/screen/">screen</a> the <a href="http://hisham.hm/htop/">htop</a> interface looks messed up. It's still usable, but you know, the eyes want to be pleased as well (yes, even in the terminal). But it sucks even more: Just split the terminal and then run <span style="font-family: "courier new" , "courier" , monospace;">cat </dev/urandom</span> in one of the splits. Chances are you'll get random garbage spewed all over <i>the other split</i> as well. Doesn't inspire much confidence in how well-isolated those splits are, does it?<br />
<br />
So of course I tried <a href="https://tmux.github.io/">tmux</a> next, a much more recent project and maybe "better" because it doesn't have as much buggy legacy code. Sadly it immediately fails the <a href="http://hisham.hm/htop/">htop</a> test as well, but at least it does a little better when hit with the random hammer: No more spewing into the other split, but still the status line gets trashed and once you stop hammering some of the UI elements are just a little out of it. A little groggy most likely?<br />
<br />
One more attempt, let's try <a href="http://www.brain-dump.org/projects/dvtm/">dvtm</a> instead. If you don't know, that's a <a href="http://dwm.suckless.org/">dwm</a> clone <i>inside</i> the terminal. And wow, it passes <i>both</i> the <a href="http://hisham.hm/htop/">htop</a> test <i>and</i> the random hammer with flying colors, only a few of the border elements get trashed. On the downside, it's least likely to be installed on a random UNIX system you need to work on. That, and it has a bunch of opinionated layout assumptions that may not be to your liking. I, however, like them just fine, at least for the most part.<br />
<br />
At this point I started asking myself what I actually need in my terminal multiplexer, and I arrived at a rather short list of features:<br />
<br />
<ul>
<li>create a new terminal window with a shell running in it (splitting the terminal area horizontally or vertically or at least sanely)</li>
<li>switch from one terminal window to another quickly and reliably</li>
<li>destroy an existing terminal window and whatever is running in it</li>
</ul>
<br />
That's really it as far as interactive use on my home machine or laptop is concerned. Sure, being able to detach and reattach sessions later is great, especially when working remotely. But for that use-case I already have <a href="https://www.gnu.org/software/screen/">screen</a> wired into my brain and fingers. (Also it turns out that <a href="http://www.brain-dump.org/projects/dvtm/">dvtm</a> doesn't persist sessions in any which way, so I'd need to use another tool like <a href="http://dtach.sourceforge.net/">dtach</a> or (more likely) <a href="http://www.brain-dump.org/projects/abduco/">abduco</a> with <a href="http://www.brain-dump.org/projects/dvtm/">dvtm</a>.)<br />
<br />
So what am I to do? Which one of these am I to learn and put deep into my muscle memory over the next few weeks? That's when it struck me: I can probably learn none of them and all of them at the same time! After all, I have <i>very</i> few requirements (see above) and as luck would have it, all of the tools are <i>highly</i> configurable. Especially in regards to their keybindings! Can it be done?<br />
<br />
<blockquote class="tr_bq">
<i>Can I configure all three tools in such a way that one set of keybindings will get me all the features I actually need?</i></blockquote>
<br />
Let's see what we find in each program for each use-case, then try to generalize from there. Let's start with <a href="https://www.gnu.org/software/screen/">screen</a>:<br />
<br />
<ul>
<li>CTRL-a-c create a new full-sized window (and start a shell) </li>
<li>CTRL-a-n switch to the next full-sized window</li>
<li>CTRL-a-p switch to the previous full-sized window</li>
<li>CTRL-a-S split current region horizontally (no shell started)</li>
<li>CTRL-a-| split current region vertically (no shell started)</li>
<li>CTRL-a-TAB switch to the next region</li>
<li>CTRL-a-X remove current region (shell turns into full-sized window)</li>
<li>CTRL-a-k kill current window/region (including the shell)</li>
<li>CTRL-a-d detach screen</li>
</ul>
<br />
So obviously the concepts of window and region are a bit strange, but for better or worse that's what we get. I am pretty sure that regions (splitting one terminal into several "subterminals") was added later? In terms of my uses cases it's a bit sad that creating a new region does not also immediately launch a shell in it, instead I have to move to the new region with CTRL-a-TAB and then hit CTRL-a-c to do that manually. It's also strange that removing a region doesn't kill the shell running in it but turns that shell into a "window" instead. And of course navigating windows is different from navigating regions. Let's see how <a href="https://tmux.github.io/">tmux</a> does it:<br />
<br />
<ul>
<li>CTRL-b-c create new full-sized window (and start a shell)</li>
<li>CTRL-b-n switch to next full-sized window</li>
<li>CTRL-b-p switch to previous full-sized window </li>
<li>CTRL-b-" split current pane horizontally (and start a shell)</li>
<li>CTRL-b-% split current pane vertically (and start a shell)</li>
<li>CTRL-b-o switch to next pane</li>
<li>CTRL-b-UP/DOWN/LEFT/RIGHT switch to pane in that direction </li>
<li>CTRL-b-x kill current pane (as well as shell running in it)</li>
<li>CTRL-b-& kill current window (as well as shell running in it) </li>
<li>CTRL-b-d detach tmux</li>
</ul>
<br />
So we can pretty much do the same things, but <i>not quite</i>. That's annoying. Note how creating a new "pane" launches a shell and how killing a "pane" kills the shell running in it? That's exactly what <a href="https://www.gnu.org/software/screen/">screen</a> <i>doesn't</i> do. Also note that <a href="https://tmux.github.io/">tmux</a> has a notion of "direction" with regards to panes, something completely lacking in <a href="https://www.gnu.org/software/screen/">screen</a>. And note that "windows" are still different from "panes" in terms of navigation. Finally, what's <a href="http://www.brain-dump.org/projects/dvtm/">dvtm</a> like?<br />
<br />
<ul>
<li>CTRL-g-c create a new window (and start a shell, splitting automatically)</li>
<li>CTRL-g-x close current window (and kill the shell running in it)</li>
<li>CTRL-g-TAB switch to previously selected window</li>
<li>CTRL-g-j switch to next window</li>
<li>CTRL-g-k switch to previous window</li>
<li>CTRL-g-SPACE switch between defined layouts</li>
<li>CTRL-\ detach (using <a href="http://www.brain-dump.org/projects/abduco/">abduco</a>, no native session support) </li>
</ul>
<br />
Note that <a href="http://www.brain-dump.org/projects/dvtm/">dvtm</a>'s notion of "window" unifies what the other two tools call "window" (full-sized) and "region" or "pane" (split-view). But the biggest difference is that <a href="http://www.brain-dump.org/projects/dvtm/">dvtm</a> actually has an <i>opinion</i> about what the layout should be. You can choose between a few predefined layouts (with CTRL-g-SPACE) but that's it. One of these layouts shows one "window" at a time, but the navigation between "windows" stays consistent regardless of how many you can see in your terminal.<br />
<br />
So what's the outcome here? Personally, I very much prefer what <a href="http://www.brain-dump.org/projects/dvtm/">dvtm</a> does over what <a href="https://tmux.github.io/">tmux</a> does over what <a href="https://www.gnu.org/software/screen/">screen</a> does. Obviously your mileage may vary, but what I'll try to do here is make all the programs behave (more or less, and within reason) like <a href="http://www.brain-dump.org/projects/dvtm/">dvtm</a>.<br />
<br />
Of course there are plenty of issues to resolve. For starters, two of the programs care about whether a split is vertical (top/bottom) or horizontal (left/right) while one doesn't. The simplest solution I can think of is to have separate key bindings for each but to map them to the same underlying command in <a href="http://www.brain-dump.org/projects/dvtm/">dvtm</a>. This way I'll learn the key bindings for the worst case while enjoying the features of the best case.<br />
<br />
Next <a href="https://www.gnu.org/software/screen/">screen</a> doesn't automatically start a shell in a new split while the other two do. Luckily that's easy to resolve by writing new and slightly more complex key bindings. There are a few additional issues we'll get into below when we talk about how to configure each program, but first we need to "switch gears" as it were: It's time to do some very basic user interface design.<br />
<br />
Let's face the most important decision first, namely which "leader key" should I use? We have CTRL-a, CTRL-b, and CTRL-g as precedents, but we don't necessarily have to follow those.<br />
<br />
I played with various keys for a while to see what's easiest for me to trigger. My favorite "leader keys" would have to be CTRL-c and CTRL-d. Sadly, those already have "deep meaning" for shells, so I don't want to use either of them. The next-best keys (for my hands anyway) would be CTRL-e and CTRL-f. Sadly, CTRL-e is used for "move to end of line" in <a href="http://www.gnu.org/software/bash/">bash</a> and I tend to use that quite a bit; <a href="https://www.gnu.org/software/screen/">screen</a>'s CTRL-a sort of shares that problem. In terms of "finger distance" I also find CTRL-a "too close and squishy" and CTRL-b/CTRL-g "too far and stretchy" for myself.<br />
<br />
Based on this very unscientific analysis, I ended up picking CTRL-f as the "unified leader key" for all three multiplexers. The drawback of this is that I'll train my muscle memory for "the wrong key" but between three programs, any key would have been "the right key" only for <i>one</i> of them anyway. Big deal. (Yes, in <a href="http://www.gnu.org/software/bash/">bash</a> CTRL-f triggers "move one character forward" but that's not really a big loss either, is it?)<br />
<br />
With the leader settled, how shall we map each use-case to actual key strokes? The guiding principle I'll follow is to rank things by how often I am likely to do them. (Of course that's just a guess for now, if it turns out to be wrong I'll adapt later.) I believe that the ranking is as follows:<br />
<br />
<ol>
<li>Navigate between splits.</li>
<li>Create a new split.</li>
<li>Remove the current split.</li>
</ol>
<br />
If that's true, then moving to the next split should be on the same key as the leader, so the sequence would be CTRL-f-f. That even works mnemonically if we interpret "f" as "forward" or something. Now let's find keys to create splits. At first I thought "something <i>around</i> f" would be good, the idea being that I'd hit the key with the same finger I used to hit "f" a moment before. But that's actually <i>slower</i> than hitting a key with another finger on the same hand. The way I type, I hit "f" with my index finger and my middle finger naturally hovers over "w" in the process. So CTRL-f-w it is, after all that's again a mnemonic, for "window" this time. But what kind of split should it be, horizontal or vertical? I settled on horizontal because in <a href="http://www.brain-dump.org/projects/dvtm/">dvtm</a>'s default layout, the first split will also be horizontal (left/right). So I'll get some consistency after all. The other key that's quick for me to hit is "e" so CTRL-f-e shall be the vertical (top/bottom) split. That leaves removing the current split, and for that CTRL-f-r is good enough, again with some mnemonic goodness. Here's the summary:<br />
<br />
<ul>
<li>CTRL-f-f switch to next split</li>
<li>CTRL-f-w split horizontally (and start a new shell)</li>
<li>CTRL-f-e split vertically (and start a new shell)</li>
<li>CTRL-f-r remove current split (and terminate the shell)</li>
</ul>
<br />
Sounds workable to me. All that remains is actually making the three programs behave "similarly enough" for those keystrokes. As per usual, we'll start with <a href="https://www.gnu.org/software/screen/">screen</a>. The file to create/edit is <span style="font-family: "courier new" , "courier" , monospace;">~/.screenrc</span> and here's what we'll do:<br />
<br />
<blockquote class="tr_bq">
<span style="font-family: "courier new" , "courier" , monospace;">hardstatus ignore</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">startup_message off</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">escape ^Ff</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind f eval "focus"</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind ^f eval "focus"</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind <span style="font-family: "courier new" , "courier" , monospace;">e</span> eval "split" "focus" "screen"</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind ^<span style="font-family: "courier new" , "courier" , monospace;">e</span> eval "split" "focus" "screen"</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind <span style="font-family: "courier new" , "courier" , monospace;">w</span> eval "split -v" "focus" "screen"</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind ^<span style="font-family: "courier new" , "courier" , monospace;">w</span> eval "split -v" "focus" "screen"</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind r eval "kill" "remove"</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind ^r eval "kill" "remove"</span></blockquote>
<br />
I'll admit right away that my understanding of "hardstatus" is lacking. What I am hoping this command does is turn off <i>any</i> status line that would cost us terminal real estate: I want to focus on the applications I am using, not on the terminal multiplexer and what it thinks of the world. The "startup_message" bit just makes sure that there's no such thing; many distros disable it by default anyway, but for some strange reason Ubuntu leaves it on. (I am all for giving people credit for their work, but that message requires a key press to go away and therefore it's annoying as heck.)<br />
<br />
The remaining lines simply establish the key bindings described above, albeit in a somewhat repetitive manner: I define each key twice, once with CTRL and once without, that way it doesn't matter how quickly I release the CTRL key during the sequence of key presses. (If you have a more concise way of doing the same thing, please let me know!)<br />
<br />
We should briefly look at what we lose compared to the default key bindings. Our use of "f" overrides "flow control" and luckily I cannot think of many reasons why there should be "flow control" these days. Our use of "w" overrides "list of windows" but since I intend to mostly use splits that's not a big problem. Our use of "e" comes for free because it's not used in the default configuration. Finally, our use of "r" overrides line-wrapping, something I don't imagine caring about a lot. So we really don't lose too much of the basic functionality here, do we?<br />
<br />
Next we need to configure <a href="https://tmux.github.io/">tmux</a>. The file to create/edit is <span style="font-family: "courier new" , "courier" , monospace;">~/.tmux.conf</span> and here's how that one works:<br />
<br />
<blockquote class="tr_bq">
<span style="font-family: "courier new" , "courier" , monospace;">set-option -g status off</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">set-option -g prefix C-f</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">unbind-key C-b</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind-key C-f send-prefix</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind-key f select-pane -t :.+</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind-key C-f select-pane -t :.+</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind-key w split-window -h</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind-key C-w split-window -h</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind-key e split-window</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind-key C-e split-window</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind-key r kill-pane</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">bind-key C-r kill-pane</span></blockquote>
<br />
Different syntax, same story. First we switch off the status bar to get one more line of terminal real estate back. Then we change the leader key to CTRL-f and define (repetitively, I know) the key bindings we settled on above. Easy. (Well, except for figuring out the select-pane arguments, I need to credit <a href="https://robots.thoughtbot.com/a-tmux-crash-course">Josh Clayton</a> for that. Yes, it's in the man page, but it's hard to grok at first.)<br />
<br />
What do we lose? By using "f" we lose the "find text in windows" functionality, something I don't foresee having much use for. By using "w" we lose "choose window interactively" which seems equally useless. Luckily "e" is once again a freebie, a key not used by the default configuration. Finally, by using "r" we lose "force redraw" which is hopefully not something I'll need very often. Seems alright by me!<br />
<br />
Last but not least, let's configure <a href="http://www.brain-dump.org/projects/dvtm/">dvtm</a>. In true <a href="http://suckless.org/">suckless</a> style there is of course <i>no configuration file</i> because that would "attract too many users with stupid questions" and the like. (Arrogance really <i>is</i> bliss, isn't it? Let me just say for the record that I really appreciate the <a href="http://suckless.org/">suckless</a> ideals and their software. But that doesn't change the fact that configuration files are convenient for <i>all</i> users (not just idiots!) who don't want to manually compile every last bit of code on their machines. But I digress...) So we have to edit <span style="font-family: "courier new" , "courier" , monospace;">config.h</span> and recompile the application, which in Gentoo amounts to (a) setting the <span style="font-family: "courier new" , "courier" , monospace;">savedconfig</span> USE flag, (b) editing the file<br />
<br />
<blockquote class="tr_bq">
<span style="font-family: "courier new" , "courier" , monospace;">/etc/portage/savedconfig/app-misc/dvtm-0.14</span></blockquote>
<br />
and then (c) re-emerging the application. Here's the (grisly?) gist of it:<br />
<br />
<blockquote class="tr_bq">
<span style="font-family: "courier new" , "courier" , monospace;">#define BAR_POS BAR_OFF</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">#define MOD CTRL('f')</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">...</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">{{MOD, 'f',}, {focusnext, {NULL}}},</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">{{MOD, CTRL('f'),}, {focusnext, {NULL}}},</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">{{MOD, 'w',}, {create, {NULL}}},</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">{{MOD, CTRL('w'),}, {create, {NULL}}},</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">{{MOD, 'e',}, {create, {NULL}}},</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">{{MOD, CTRL('e'),}, {create, {NULL}}},</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">{{MOD, 'r',}, {killclient, {NULL}}},</span><br />
<span style="font-family: "courier new" , "courier" , monospace;">{{MOD, CTRL('r'),}, {killclient, {NULL}}},</span><br />
<span style="font-family: "courier new" , "courier" , monospace;"></span></blockquote>
<br />
There are a few more modifications I didn't show, but just to remove existing key bindings that conflict with ours. Which brings us to the question what we lose. Our use of "f" costs us the ability to choose one specific layout, something I can live without for sure. Our use of "w" is a freebie, it's unused by default. Our use of "e" costs us "copymode" which, so far, I didn't need; eventually I may have to revisit this decision and maybe remap the functionality elsewhere. Finally, our use of "r" costs us being able to "redraw" the screen, something I hope I won't need too much.<br />
<br />
Wow, what a project. Had I known I'd spend about 10 hours on learning all the relevant things and writing this blog post, maybe I would not ever have started. But now that it's all done, I am actually enjoying the fruits of my labor: Splitting my terminal regardless of what ancient UNIX system I am on? Using fancier tools on newer machines, including my own? Debugging client/server stuff with a lot less need to grab the mouse and click something? It's paradise! Well, close to it anyway...<br />
<br />
<b>Update 2016/04/23:</b> My "unified" configuration files are now available on <a href="https://github.com/phf/sutm">github.com</a> if you want to grab them directly.Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com2tag:blogger.com,1999:blog-2240283907729630332.post-17504458459439302102016-03-02T01:40:00.002+01:002016-03-02T01:40:36.478+01:00Revision Control MattersI am currently teaching our project course in video game design again. I decided early on that all student teams should use a revision control system, specifically <a href="https://git-scm.com/">git</a> through <a href="http://bitbucket.org/">Bitbucket</a>, to coordinate their work. Sadly I did run into some resistance regarding this requirement with many students stating that <a href="http://www.dropbox.com/">Dropbox</a> and <a href="http://www.google.com/drive/">Google Drive</a> are much more convenient for them. So I thought I'd ask around among my game development friends for opinions, and I got a few. But first let me paraphrase my "official" question to them:<br />
<br />
<blockquote class="tr_bq">
<i>In your esteemed
opinion, how important is it for people working on a video game together
to be able to use a revision control system to coordinate their work?
How many of you have, in your gaming work, been able to get away without
using one? Do you think it's less important for artists? How about
artists who not only produce art (graphics, sound, etc.) but also write
code/scripts?</i></blockquote>
<br />
The answers below are in no particular order. For some I've cleaned up the grammar a little. I've also "anonymized" the people involved because I wasn't sure how they'd like being quoted in public. But rest assured that they are all experienced software developers who've done at least several gaming projects. Let's start with JB:<br />
<br />
<blockquote class="tr_bq">
<i>This
is beyond question. Just no question. ... I would <b>never</b> work
without a revision control system, even
working by myself. Working with a team, running the committed code
through automated tests every night, (yelling at the person who broke
the code is beyond satisfying), staying in sync, knowing that everything
everyone is doing will continuously still work together—mandatory.
You <b>will</b> encounter crunch-time bugs that can only be found by rolling back
trough revisions until the bug doesn't exist. And you want to be
creative and unlimited? Branching ... so you can try out something radical is priceless!<span data-ft="{"tn":"K"}"><span class="UFICommentBody _1n4g"> ... You <b>will</b> learn why you need revision control systems eventually, no
matter how thick you are. But at the end of the day, you want to
work for a good company with excellent people, and they aren't
going to want <b>you</b> unless you are on board with revision control systems. End of
story. It's a career requirement. So suck it up buttercup.</span></span></i></blockquote>
<br />
Next we have AD with a slightly different opinion:<br />
<br />
<blockquote class="tr_bq">
<i>I would not force students who are resisting. Things like Dropbox provide data sharing which is most of what 1–2 programmer teams need. If they lose their code you can always make fun of them. Personally I always use revision control but my games are very code-centric and I came into game development with a software engineering background. One of the things I like about games is that nobody cares about code or tools—only results. Most software engineers are evaluated by other software engineers and a lot of quasi-religious groupthink comes out of that. Game development is a reality check: Can I <b>really</b> use these software skills to produce something <b>normal</b> people want? Software engineering classes are a better place to force students to learn about revision control, the game development kids should focus on making fun games with minimum friction.</i></blockquote>
<br />
I should say that the student teams in our course are 4–5 students, not 1–2 as AD had assumed. And please note that AD still holds students responsible in case their ad-hoc approach fails. Next we have DC:<br />
<br />
<blockquote class="tr_bq">
<i>For the past few weeks I've been working on a simulator <b>entirely on my own</b> and I'm <b>still</b> kicking myself for not using version control: I've noticed a change in the outputs in the last couple days that is inexplicable and I don't have a recent snapshot I can go back to to track down what caused it. Certainly I've never worked at a game company, or heard about any acquaintances doing so, that failed to use version control. It's a universal standard. Should it be required of the students? Arguments in both directions: (a) using it gets them experience with an industry standard; (b) not using it will force them to confront the problems that crop up, and deeply understand why they want version control in the future. ... I usually side with (a) although I was just reading a part of the JHU orientation which ... emphasizes students learning more on their own.</i></blockquote>
<br />
It's true that we try to encourage "learning on your own" and I guess my courses are particularly "infamous" in that regard. However, I would still hold that it's appropriate to force students to do it, in a company environment they most likely would be "forced" as well. But hey, now I am throwing too much of my own perspective in here. Let's get to AS:<br />
<br />
<blockquote class="tr_bq">
<i>It's a requirement!</i></blockquote>
<br />
That's certainly the most succinct reply I received. So on to SC:<br />
<br />
<blockquote class="tr_bq">
<i>I'd say it's a requirement for the code base at the very least. Git or Perforce can be punishing with Unity files, but it's ultimately best. Art I'm more flexible with. An old job tried to handle art with Git and it was bad. Currently our artists maintain stuff on their own Perforce server (since it's unlikely that more than one artist is working on any given asset) and then upon completion things move to the Unity repository. </i></blockquote>
<br />
The point here is that art assets are hard to merge automatically and so a system that allows "locking" is preferable over one that forces merging. Note, however, that there's still a revision control system in place, albeit a different one. I don't have a way to give students Perforce licenses, but maybe <a href="http://www.fossil-scm.org/">Fossil</a> <a href="http://www.fossil-scm.org/xfer/wiki?name=Fossil+2.0">2.0</a> will be an option in the future. Of course <a href="http://subversion.apache.org/">Subversion</a> supports <a href="http://svnbook.red-bean.com/en/1.7/svn.advanced.locking.html">locking</a> as well, it just feels slightly antiquated these days. Next we have BR:<br />
<br />
<blockquote class="tr_bq">
<i>I was able to get away without one... In Nineteen Ninety Freaking Six!</i></blockquote>
<br />
Speaks for itself, doesn't it? On to NMC's opinion:<br />
<br />
<blockquote class="tr_bq">
<i>Sometimes, for a small project with only one person working on it, you can get away just periodically taking your entire project folder and compressing it to a zip file. This is barely adequate for one person working alone on a recreational project, and even in that situation version control would make your life easier.</i></blockquote>
<br />
I think I am starting to see a pattern here, don't you? Finally we have JC (who refers back to BR above):<br />
<br />
<blockquote class="tr_bq">
<i>Is it <b>essential</b> for every project? No. Is it <b>useful</b> for every project? Yes. A career hallmark of game development (and maybe the tech industry itself) is enjoying learning new things constantly. There is <b>always</b> a better way. Either you love that or you think you've learned enough. The people who think they know enough don't tend to last or have passed into a phase of their career that likely won't last in a satisfying way. Our current view is Git (or Hg) for code and Perforce for content. They just make life easier. For the size of Unity projects you will encounter in college, Git (or Hg) alone is totally fine.</i><br />
<i><br /></i>
<i>Git is something that everyone hates and don't understand if they use it rarely. If they use it regularly, they usually love it. It's crazy fast and lets you do all the things you want to do. Perforce is nice in that it is rock-solid and handles large binaries well. But you also lose information everytime you merge (unlike a distributed system) and branching is painful, particularly after the fact. And, of course, it isn't free ...</i><br />
<i><br /></i>
<i>I probably agree with BR: let them do whatever but no excuses accepted for lost work. That is the reality. But it's definitely a plus for us as a company when an entry-level candidate has real experience with the major source control systems. For one, it's just a skill like anything else. But, second, it gives some indication that they've done enough work to understand the value.</i><br />
<i><br /></i>
<i>On a side note: BR "got away with it" until I was hand-merging changes from him and SM every day ... in addition to writing the core game systems. To his credit, BR fully supported the change. And, agh, we used SourceSafe. <b>That</b> I would not recommend. </i></blockquote>
<br />
Seems to me that this (biased?) sample of opinions tends to agree with my feeling that every student should learn how to work with a revision control system. So I for my part feel "vindicated" as it were.<br />
<br />
If you're a student in one of my project courses and you hate the idea of learning a revision control system, re-read these comments from industry professionals a few times. Then ask yourself if you'd rather be able to say, truthfully, that you learned something like git or if you'd rather apologize that you didn't. Your call, but I am almost certain that your answer will have an effect on your chances of getting hired.<br />
<br />
(I'd like to thank everybody who answered my question back when I posted it on Facebook. You're the best!)Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com0tag:blogger.com,1999:blog-2240283907729630332.post-56101741322871387502016-02-21T00:16:00.000+01:002016-02-21T00:16:06.543+01:00What to do with a new disk?Today two replacement SATA disks arrived from my <a href="http://www.newegg.com/">favorite supplier</a>. Reason enough to briefly summarize what I do when I get fresh disks: Maybe someone else can learn from the DOA mistakes of my youth when I trusted that a new disk would just work only to find that when I needed it, all it would do is "click click click" and that was that.<br />
<br />
If you go through more disks than the average person, for example because you run a bunch of RAID arrays, I would first recommend that you get yourself a suitable docking station. Here's what I use:<br />
<br />
<table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto; text-align: center;"><tbody>
<tr><td style="text-align: center;"><a href="https://4.bp.blogspot.com/-Xms_TvK5d0c/Vsjnj4D3IbI/AAAAAAAAB44/UX0G2k9DhME/s1600/A2BP_130409675537738295sGSQw6HjIk.jpg" imageanchor="1" style="margin-left: auto; margin-right: auto;"><img alt="UNITEK Dual Bay USB Docking Station" border="0" height="300" src="https://4.bp.blogspot.com/-Xms_TvK5d0c/Vsjnj4D3IbI/AAAAAAAAB44/UX0G2k9DhME/s400/A2BP_130409675537738295sGSQw6HjIk.jpg" title="UNITEK Dual Bay USB Docking Station" width="400" /></a></td></tr>
<tr><td class="tr-caption" style="text-align: center;">UNITEK Dual Bay USB Docking Station</td></tr>
</tbody></table>
<br />
I got mine from <a href="http://www.newegg.com/Product/Product.aspx?Item=9SIA2BP1A26627">newegg.com</a> of course. There are plenty of alternatives, little USB-to-SATA adapters or hotswap bays that mount in your machine's case, but none of those beat a decent docking station for convenience and versatility. (Note that I never use the "clone" feature of that thing, although I hear that it works fine.)<br />
<br />
So unpack your new disks and do a quick physical inspection. If your supplier is decent at all, the packaging will be so good that it's extremely unlikely that you'll get something that's mechanically broken on the outside, so a glance is usually enough. Then slap them into your docking station and power it up. Open a terminal and do a quick check with <b>dmesg</b>:<br />
<br />
<blockquote class="tr_bq">
<span style="font-size: x-small;"><span style="font-family: "Courier New",Courier,monospace;">[51407.603023] usb 1-1: new high-speed USB device number 4 using ehci-pci<br />[51407.718674] usb 1-1: New USB device found, idVendor=152d, idProduct=2551<br />[51407.718678] usb 1-1: New USB device strings: Mfr=1, Product=11, SerialNumber=3<br />[51407.718679] usb 1-1: Product: USB Mass Storage<br />[51407.718681] usb 1-1: Manufacturer: JMicron<br />[51407.718682] usb 1-1: SerialNumber: 00000000000000<br />[51407.719191] usb-storage 1-1:1.0: USB Mass Storage device detected<br />[51407.719353] scsi host6: usb-storage 1-1:1.0<br />[51408.142938] usbcore: registered new interface driver uas<br />[51409.223243] scsi 6:0:0:0: Direct-Access HDD 0000 PQ: 0 ANSI: 2 CCS<br />[51409.224849] scsi 6:0:0:1: Direct-Access HDD 0000 PQ: 0 ANSI: 2 CCS<br />[51409.225220] sd 6:0:0:0: Attached scsi generic sg6 type 0<br />[51409.225355] sd 6:0:0:1: Attached scsi generic sg7 type 0<br />[51409.229108] sd 6:0:0:0: [sdf] 1953525168 512-byte logical blocks: (1.00 TB/931 GiB)<br />[51409.229476] sd 6:0:0:1: [sdg] 1953525168 512-byte logical blocks: (1.00 TB/931 GiB)<br />[51409.230360] sd 6:0:0:0: [sdf] Write Protect is off<br />[51409.230365] sd 6:0:0:0: [sdf] Mode Sense: 28 00 00 00<br />[51409.231358] sd 6:0:0:1: [sdg] Write Protect is off<br />[51409.231363] sd 6:0:0:1: [sdg] Mode Sense: 28 00 00 00<br />[51409.232350] sd 6:0:0:0: [sdf] No Caching mode page found<br />[51409.232355] sd 6:0:0:0: [sdf] Assuming drive cache: write through<br />[51409.233613] sd 6:0:0:1: [sdg] No Caching mode page found<br />[51409.233616] sd 6:0:0:1: [sdg] Assuming drive cache: write through<br />[51409.286473] sd 6:0:0:0: [sdf] Attached SCSI disk<br />[51409.287473] sd 6:0:0:1: [sdg] Attached SCSI disk</span></span></blockquote>
<br />
Alright, looks like both disks are there having been recognized when the docking station powered up. Good! Now go ahead and check the details with <b>smartctl</b>:<br />
<br />
<blockquote class="tr_bq">
<span style="font-size: x-small;"><span style="font-family: "Courier New",Courier,monospace;"># smartctl -i /dev/sdf -d sat<br />smartctl 6.4 2015-06-04 r4109 [x86_64-linux-4.1.12-gentoo] (local build)<br />Copyright (C) 2002-15, Bruce Allen, Christian Franke, www.smartmontools.org<br /><br />=== START OF INFORMATION SECTION ===<br />Model Family: Seagate Barracuda 7200.14 (AF)<br />Device Model: ST1000DM003-1SB10C<br />Serial Number: Z9A0GYZ0<br />LU WWN Device Id: 5 000c50 08774c950<br />Firmware Version: CC43<br />User Capacity: 1,000,204,886,016 bytes [1.00 TB]<br />Sector Sizes: 512 bytes logical, 4096 bytes physical<br />Rotation Rate: 7200 rpm<br />Form Factor: 3.5 inches<br />Device is: In smartctl database [for details use: -P show]<br />ATA Version is: ATA8-ACS T13/1699-D revision 4<br />SATA Version is: SATA 3.0, 6.0 Gb/s (current: 3.0 Gb/s)<br />Local Time is: Sat Feb 20 17:34:31 2016 EST<br />SMART support is: Available - device has SMART capability.<br />SMART support is: Enabled<br /># smartctl -i /dev/sdg -d sat<br />smartctl 6.4 2015-06-04 r4109 [x86_64-linux-4.1.12-gentoo] (local build)<br />Copyright (C) 2002-15, Bruce Allen, Christian Franke, www.smartmontools.org<br /><br />=== START OF INFORMATION SECTION ===<br />Model Family: Western Digital Blue<br />Device Model: WDC WD10EZEX-00WN4A0<br />Serial Number: WD-WMC6Y0F4UPT5<br />LU WWN Device Id: 5 0014ee 0aec80cac<br />Firmware Version: 01.01A01<br />User Capacity: 1,000,204,886,016 bytes [1.00 TB]<br />Sector Sizes: 512 bytes logical, 4096 bytes physical<br />Rotation Rate: 7200 rpm<br />Form Factor: 3.5 inches<br />Device is: In smartctl database [for details use: -P show]<br />ATA Version is: ACS-3 T13/2161-D revision 3b<br />SATA Version is: SATA 3.1, 6.0 Gb/s (current: 3.0 Gb/s)<br />Local Time is: Sat Feb 20 17:34:57 2016 EST<br />SMART support is: Available - device has SMART capability.<br />SMART support is: Enabled</span></span></blockquote>
<br />
Good! Notice that I had to use the "<span style="font-family: "Courier New",Courier,monospace;">-d sat</span>" option to tell smartctl that there's really a SATA drive hiding behind all the USB stuff. (Took me a while to realize that I can do that, I used to think that SMART just doesn't work at all over USB.)<br />
<br />
What you want to be looking for is the "<span style="font-family: "Courier New",Courier,monospace;">SMART support is:</span>" line. It's almost universally true today that SMART will be enabled by default, unlike back in 2002. But it's still good to check. In case it's not enabled, enable it. In case your disk doesn't support SMART at all, well, why did you order it? To enable SMART you'd say something like<br />
<br />
<blockquote class="tr_bq">
<span style="font-size: x-small;"><span style="font-family: "Courier New",Courier,monospace;"># smartctl -s on /dev/sdf -d sat</span></span></blockquote>
<br />
but again, hopefully you won't have to. Alright, after all this prep work, we finally get to the point of all this: You want to run the basic SMART tests that all modern drives support. Note that especially the long test can take a really long time, so do this when you're sure you won't need the docking station for something else. First run the short tests:<br />
<br />
<blockquote class="tr_bq">
<span style="font-family: "Courier New",Courier,monospace;"><span style="font-size: x-small;"># smartctl -t short /dev/sdf -d sat</span></span><br />
<span style="font-family: "Courier New",Courier,monospace;"><span style="font-size: x-small;"># smartctl -t short /dev/sdg -d sat</span></span></blockquote>
<br />
Yes, you can easily run these in parallel because the <b>disk</b> is doing its own testing, your machine only told it to get going. For a 1 TB disk, the short test takes about a minute, but if you're impatient, you can check on the progress of the test as follows:<br />
<br />
<blockquote class="tr_bq">
<span style="font-family: "Courier New",Courier,monospace;"><span style="font-size: x-small;"># smartctl -a /dev/sdf -d sat</span></span><br />
<span style="font-family: "Courier New",Courier,monospace;"><span style="font-size: x-small;">...<br />=== START OF INFORMATION SECTION ===<br />Model Family: Seagate Barracuda 7200.14 (AF)<br />...</span></span><br />
<span style="font-family: "Courier New",Courier,monospace;"><span style="font-size: x-small;">=== START OF READ SMART DATA SECTION ===<br />SMART overall-health self-assessment test result: PASSED<br />...</span></span><br />
<span style="font-family: "Courier New",Courier,monospace;"><span style="font-size: x-small;">Self-test execution status: ( 246) Self-test routine in progress... 60% of test remaining.</span></span><br />
<span style="font-family: "Courier New",Courier,monospace;"><span style="font-size: x-small;">...</span></span></blockquote>
<br />
There's a <b>lot</b> more output than that, I just put "..." instead to keep things simple. (Actually you can get even more output with <span style="font-family: "Courier New",Courier,monospace;">-x</span> instead of <span style="font-family: "Courier New",Courier,monospace;">-a</span> if you really want.) After waiting for your minute, you can check on the outcome of the test with the same command. Toward the bottom of the output you'll hopefully find a line like the following:<br />
<br />
<blockquote class="tr_bq">
<span style="font-size: x-small;"><span style="font-family: "Courier New",Courier,monospace;">SMART Self-test log structure revision number 1<br />Num Test_Description Status Remaining LifeTime(hours) LBA_of_first_error</span></span><span style="font-size: x-small;"><span style="font-family: "Courier New",Courier,monospace;"></span></span><br /><span style="font-size: x-small;"><span style="font-family: "Courier New",Courier,monospace;"># 1 Short offline Completed without error 00% 0 -</span></span></blockquote>
<br />
This indicates that the short test succeeded. Check the other disk as well, then get ready for the long test:<br />
<br />
<blockquote class="tr_bq">
<span style="font-family: "Courier New",Courier,monospace;"><span style="font-size: x-small;"># smartctl -t long /dev/sdf -d sat</span></span><br />
<span style="font-family: "Courier New",Courier,monospace;"><span style="font-size: x-small;"># smartctl -t long /dev/sdg -d sat</span></span></blockquote>
<br />
Same procedure as before, except that this time you can expect to wait for about two hours for a 1 TB disk. Hopefully the long test also works out just fine.<br />
<br />
And there you have it, the minimum amount of testing I do on replacement disks these days before I put them on the shelf as I wait for a RAID array to fail. Of course if you have plans to <a href="http://nilisnotnull.blogspot.com/2015/04/better-be-at-least-this-paranoid.html">encrypt the data on these disks</a> you can do more "testing" by <a href="http://nilisnotnull.blogspot.com/2015/04/how-paranoid-would-you-like-to-be-today.html">filling them up with random data</a> now before you shelf them away.Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com3tag:blogger.com,1999:blog-2240283907729630332.post-65411861718669514062016-02-03T00:08:00.004+01:002016-02-03T00:08:36.995+01:00Tired of Bernie DetractorsThe recent uptick in so-called "liberal" commentators telling people who want to vote for Bernie Sanders why they shouldn't and why Hillary Clinton is the better candidate has me moderately pissed-off. It's true, you can never change anyone's mind on the Internet, but it's been so long since my last political post on this blog that I figured I should take a shot.<br />
<br />
One of the first things you'll hear critics say is that Bernie stands for "wide-eyed idealists" which is a nice way of saying "idiot children who have no clue" in what passes for political discourse here in the US. Hillary of course stands for the "hard-eyed realists" which is to say "smart grown-ups who know the system" or whatever other "serious" thing. And heck, it may well be true that Bernie is an idealist and Hillary is not. What you should question, however, is if the valuation implied in most "think pieces" on this topic is correct: <b>Is it <i>actually</i> true that a "realist" president is better for the country than an "idealist" president?</b><br />
<br />
Think, for example, about how you haggle at a flea market or a garage sale. If the seller wants $10 for their lamp and you want to pay $5 for it, do you offer $9? Of course not! You offer $2 or, if you're feeling nice, maybe $3. You can't offer $1 because you know for sure that the seller will shrug their shoulders and wave you on. But offering $9 right away is actually an <i>insane</i> proposition, isn't it? Would you <i>really</i> "haggle" like that?<br />
<br />
Yet this is what so-called "experts" bring up as a "plus" for Hillary: Since she's "realist enough" to offer $9, she might actually be able to get that for us. Big surprise there! If you propose to replace, say, really bad inequality with ever-so-slightly less bad inequality, you're going to find quite a few multi-billionaires who'll say "<i>Alright, maybe I'll give up a few million here or there, at least I'll get to keep my head on my shoulders.</i>" and then you can give a State of the Union address that sells this pile of garbage as a huge success.<br />
<br />
But remember what you wanted to pay: $5! Bernie might actually be "idealist enough" to offer $3 and then achieve $6 after some back and forth. Perfect? Probably not. But without someone <i>actually haggling</i> you'll just end up with $9. Or maybe $11: After all, in politics, unlike at a semi-sane garage sale, the "other side" has already raised their expectation to $13 between the time they told you $10 and the time they hear your $9 offer. That would make it even <i>more</i> important to have an "idealist" in office, wouldn't it?<br />
<br />
Another thing you'll hear bandied about a lot is that Bernie will simply be blocked by Congress regarding every single proposal his administration might make. Once again this might be true, maybe Congress really would be more adversarial toward Bernie than toward Hillary. But again you should carefully think about the implications of this so-called "argument": <b>If it's true that President <i>Bernie</i> can be blocked by Congress, isn't it also true that President <i>Hillary</i> can be blocked?</b> Or President Donald?<br />
<br />
Note that it's irrelevant whether President X will <i>actually</i> be blocked. That's simply one for the history books because you can only know it in retrospect. Indeed, anyone who is "predicting" it as a <i>certainty</i> for Bernie now is simply being dishonest. Politics is a dynamic process after all, and Bernie might be able to play his cards in such a way that Congress will eventually go along. (Maybe by starting to haggle at $3 instead of $9?)<br />
<br />
Furthermore most of the "he'll be blocked" folks seem to completely forget that the President is <i>not powerless</i> in a fight with Congress: The veto allows a president to simply stop legislation coming out of Congress. That's not always easy, but it's clearly the case that a "mean Bernie" might be able to veto enough stuff to really make the legislative sweat. Don't forget that representatives and senators come from certain states, and if their states don't get something because of a presidential veto, the people responsible might find their incumbancy in grave danger. True, there might also be some "collateral damage" because "normal people" in those states might not get something they really need. But if the goal is to <i>fix the whole country</i> and not just a state here or a state there, well, that might be a sacrifice some of us are willing to make.<br />
<br />
And of course Congress is not the only thing that can "block" a president. The "virtual senate" of bankers and traders around the world can achieve much the same simply by shifting capital around in such a way as to hurt a country until some policy (whether proposed by President or Congress) is "off the table" again. That's in fact in large part how "neoliberal austerity" works in places that are not officially beholden to Washington's machinery of World Bank and International Monetary Fund. (Hillary actually has experienced that first-hand back during Bill Clinton's first term when they tried to pass a semi-decent healthcare bill but were promptly shut down by Wall Street.)<br />
<br />
As Iowa showed yesterday, Bernie has some <i>real</i> momentum. He also has better policies (for the 99% that is) regarding almost everything. Hillary will be "more of the same" just like her husband was (for the 1% that is). I cannot for the life of me imagine how the country could be "worse off" with Bernie than with any of the alternatives. But I can see plenty of things that <i>could be better</i> with Bernie. I am a card-carrying skeptic <i>and</i> cynic of course: It might turn out that Bernie is also "more of the same" in the end, who knows? What we know for sure is that with Donald or Hillary we're guaranteed that nothing gets better. With Bernie we at least have a shot. I am willing to take that chance, and I am tired of people who smear Bernie with "arguments" that are none.Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com2tag:blogger.com,1999:blog-2240283907729630332.post-48251527726992633412016-01-13T15:35:00.001+01:002016-01-13T15:35:10.501+01:00Basement Delving: Teenage Mutant Ninja TurtlesI have no idea why I bought all of these except that they were on a <i>superb </i>sale back in the day. I <i>did</i> like the old <b>Palladium RPG</b> as well as <b>Rifts</b> to some extent, but I never really was into <b>TMNT</b> regardless of context. Anyone out there in the greater vicinty of Munich who's interested in getting a hold of these?<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://1.bp.blogspot.com/-2TMmZNhRjhM/VpZfYnVWDQI/AAAAAAAAB2M/3cA2p-HZ6W4/s1600/DSCN5784-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="200" src="http://1.bp.blogspot.com/-2TMmZNhRjhM/VpZfYnVWDQI/AAAAAAAAB2M/3cA2p-HZ6W4/s200/DSCN5784-cut-color-small.JPG" width="150" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://3.bp.blogspot.com/-f55rOH8HYOg/VpZflNBazbI/AAAAAAAAB2U/ogU4f3CJtsA/s1600/DSCN5785-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="200" src="http://3.bp.blogspot.com/-f55rOH8HYOg/VpZflNBazbI/AAAAAAAAB2U/ogU4f3CJtsA/s200/DSCN5785-cut-color-small.JPG" width="150" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://2.bp.blogspot.com/-Pi8xbuOP4DQ/VpZflWdFzdI/AAAAAAAAB2Y/zbFx9RJjZiI/s1600/DSCN5786-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="200" src="http://2.bp.blogspot.com/-Pi8xbuOP4DQ/VpZflWdFzdI/AAAAAAAAB2Y/zbFx9RJjZiI/s200/DSCN5786-cut-color-small.JPG" width="150" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://2.bp.blogspot.com/-bfeeIx9rvc4/VpZfm4n6M0I/AAAAAAAAB2k/FUKNu9Qte64/s1600/DSCN5787-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="200" src="http://2.bp.blogspot.com/-bfeeIx9rvc4/VpZfm4n6M0I/AAAAAAAAB2k/FUKNu9Qte64/s200/DSCN5787-cut-color-small.JPG" width="150" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://3.bp.blogspot.com/-8d5ElaZh75U/VpZfn_X1HlI/AAAAAAAAB2s/Jg6ErLesLZk/s1600/DSCN5788-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="200" src="http://3.bp.blogspot.com/-8d5ElaZh75U/VpZfn_X1HlI/AAAAAAAAB2s/Jg6ErLesLZk/s200/DSCN5788-cut-color-small.JPG" width="150" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://3.bp.blogspot.com/-BEfXPi9ybwQ/VpZfojvhUbI/AAAAAAAAB2w/hkFQVS0rEgk/s1600/DSCN5789-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="200" src="http://3.bp.blogspot.com/-BEfXPi9ybwQ/VpZfojvhUbI/AAAAAAAAB2w/hkFQVS0rEgk/s200/DSCN5789-cut-color-small.JPG" width="150" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://1.bp.blogspot.com/-0-1NXLHW6CA/VpZfpHh9MFI/AAAAAAAAB20/_VUtcgu_REY/s1600/DSCN5790-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="200" src="http://1.bp.blogspot.com/-0-1NXLHW6CA/VpZfpHh9MFI/AAAAAAAAB20/_VUtcgu_REY/s200/DSCN5790-cut-color-small.JPG" width="150" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://4.bp.blogspot.com/-u0dUkmuPwoM/VpZfqRHTJxI/AAAAAAAAB3A/mwEdWUOTWo4/s1600/DSCN5791-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="200" src="http://4.bp.blogspot.com/-u0dUkmuPwoM/VpZfqRHTJxI/AAAAAAAAB3A/mwEdWUOTWo4/s200/DSCN5791-cut-color-small.JPG" width="150" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://4.bp.blogspot.com/-ymOee-i6Yro/VpZfqyAMnyI/AAAAAAAAB3E/Wv7S9UEPj-w/s1600/DSCN5792-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="200" src="http://4.bp.blogspot.com/-ymOee-i6Yro/VpZfqyAMnyI/AAAAAAAAB3E/Wv7S9UEPj-w/s200/DSCN5792-cut-color-small.JPG" width="150" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://2.bp.blogspot.com/-DWxlC21C1Zk/VpZfr8ty0gI/AAAAAAAAB3Q/Cd0hTgrldPw/s1600/DSCN5793-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="200" src="http://2.bp.blogspot.com/-DWxlC21C1Zk/VpZfr8ty0gI/AAAAAAAAB3Q/Cd0hTgrldPw/s200/DSCN5793-cut-color-small.JPG" width="150" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://4.bp.blogspot.com/-WBPRDmCxnFA/VpZfyJIFRvI/AAAAAAAAB3Y/TFAZqRbsIeA/s1600/DSCN5794-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="200" src="http://4.bp.blogspot.com/-WBPRDmCxnFA/VpZfyJIFRvI/AAAAAAAAB3Y/TFAZqRbsIeA/s200/DSCN5794-cut-color-small.JPG" width="150" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://4.bp.blogspot.com/-h0pulxR86qw/VpZfyePlbQI/AAAAAAAAB3c/DJTjk94UEI4/s1600/DSCN5795-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="200" src="http://4.bp.blogspot.com/-h0pulxR86qw/VpZfyePlbQI/AAAAAAAAB3c/DJTjk94UEI4/s200/DSCN5795-cut-color-small.JPG" width="150" /></a></div>
<br />Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com0tag:blogger.com,1999:blog-2240283907729630332.post-75274943524291549862016-01-13T10:27:00.001+01:002016-01-13T10:27:21.843+01:00Simple Hit LocationsI have a house rule that says "<i>once a character is below 0 hit points there's a chance for a permanent injury/consequence</i>" but I always winged it (or just ignored my own rule) in the heat of things. Now I decided that I want a "formally written-down rule" to resolve these injuries which at the very least requires a way to determine where the injury is located. Sure, in D&D we usually avoid this level of detail, but since this mechanic is <i>not </i>used during combat (as a critical hits chart would) I think it's okay.<br />
<br />
In any case, what is a useful distribution of hit locations? As per usual I started by looking at what others had done before. I played <a href="https://en.wikipedia.org/wiki/RuneQuest" target="_blank">RuneQuest</a> as well as <a href="https://en.wikipedia.org/wiki/Warhammer_Fantasy_Roleplay" target="_blank">Warhammer</a> back in the 1980s so I looked at those as well as <a href="http://www.mongoosepublishing.com/rpgs/legend.html" target="_blank">Legend</a>, a recent reincarnation of RuneQuest. I also acquired <a href="https://en.wikipedia.org/wiki/Flashing_Blades" target="_blank">Flashing Blades</a> and <a href="https://en.wikipedia.org/wiki/Aftermath!" target="_blank">Aftermath!</a> from <a href="http://www.fantasygamesunlimited.net/" target="_blank">Fantasy Games Unlimited</a> last year and while Flashing Blades is quite sane and included here I skipped the crazy that is Aftermath. I am sure that there are many more systems out there, but I hope four of them are enough for a first approximation.<br />
<br />
As opposed to Aftermath, all the systems I discuss here are fairly coarse-grained. Instead of giving you "shoulder" and "upper arm" and "elbow" and "lower arm" and "hand" they just give you "arm" and that's it. I happen to think that a lower resolution is preferable both because it keeps the table concise and because it is a lot more difficult to judge how "realistic" the percentages are if many fine-grained hit locations are given.<br />
<br />
Among the systems examined Warhammer is the only one that combines "chest" and "abdomen" into "body" and is therefore even more coarse-grained. Besides those areas, all systems cover "head" and "arms" and "legs," the only difference is the percentages they assign to each area. All systems except for Flashing Blades distribute hits evenly between the left and right sides of a defender; Flashing Blades assumes that a right-handed defender is more likely to get hit in the right arm than the left arm and vice versa. Only RuneQuest makes a distinction between hit locations for melee combat and missile fire. Finally, all systems except for Warhammer use a d20 to determine hit locations; Warhammer uses a d100 instead, but the ranges still come in 5% increments and we can therefore map it back onto a d20 roll as well. We end up with the following:<br />
<br />
<table style="text-align: center;">
<tbody>
<tr>
<th>Location</th><th>Flashing Blades (Right)</th><th>Legend (Mongoose)</th><th>RuneQuest (Melee)</th><th>RuneQuest (Missile)</th><th>Warhammer (1st edition)</th>
</tr>
<tr>
<td>Head</td><td>10% (1-2)</td><td>10% (19-20)</td><td>10% (19-20)</td><td>5% (20)</td><td>15% (1-3)</td>
</tr>
<tr>
<td>Right Arm</td><td>15% (3-5)</td><td>15% (13-15)</td><td>15% (13-15)</td><td>10% (16-17)</td><td>20% (4-7)</td>
</tr>
<tr>
<td>Left Arm</td><td>10% (11-12)</td><td>15% (16-18)</td><td>15% (16-18)</td><td>10% (18-19)</td><td>20% (8-11)</td>
</tr>
<tr>
<td>Abdomen</td><td>20% (13-16)</td><td>15% (7-9)</td><td>15% (9-11)</td><td>20% (7-10)</td><td><i>25% (12-16)</i></td>
</tr>
<tr>
<td>Chest</td><td>25% (6-10)</td><td>15% (10-12)</td><td>5% (12)</td><td>25% (11-15)</td><td><i>25% (12-16)</i></td>
</tr>
<tr>
<td>Right Leg</td><td>10% (17-18)</td><td>15% (1-3)</td><td>20% (1-4)</td><td>15% (1-3)</td><td>10% (17-18)</td>
</tr>
<tr>
<td>Left Leg</td><td>10% (19-20)</td><td>15% (4-6)</td><td>20% (5-8)</td><td>15% (4-6)</td><td>10% (19-20)</td>
</tr>
</tbody></table>
<br />
Sorry, not exactly easy to read. Let's look at what Warhammer calls "body" first, so "abdomen" and "chest" in terms of the table. The systems vary widely in what they consider appropriate: Flashing Blades as well as RuneQuest (for missiles) assign 45% of hits here, Legend 30%, Warhammer 25%, and RuneQuest (for melee) only 20%. Among the systems that distinguish "abdomen" from "chest" there is little agreement on what's more likely to get hit either, except (once again) in the case of Flashing Blades and RuneQuest (for missiles). I find this rather disturbing, I would have thought that we'd see at least <i>some</i> consistency here.<br />
<br />
There is a little less variation when it comes to the extremities, alas it's still quite significant. Flashing Blades and Warhammer consider leg hits rather unlikely with a 20% total, RuneQuest (for melee) thinks they are quite likely with a 40% total. On the other hand Warhammer tells us that arm hits are very common with 40% when most of the other systems assign 25%-30% instead. In general Warhammer seems "top heavy," Flashing Blades and RuneQuest (for missiles) seem "body focused," and RuneQuest (for melee) is a little "bottom heavy" as it were. Legend spreads things out most evenly.<br />
<br />
Let's not forget what we're looking for though: I want a roll that happens <i>after</i> combat when a character is already "out" because they reached 0 hit points. I don't want to assume that the "last blow" is the one the actually leads to that "grievous injury" as it were, it could have been any of the preceeding hits as well. So I don't really need those little differences that Flashing Blades and RuneQuest support regarding handedness and melee versus missile. Indeed, since my consideration is cumulative over the last couple of hits, I should probably "aim" for a more evenly distributed system. Thus Legend should provide a useful starting point.<br />
<br />
Once we settle on an even distribution, we can reconsider the die roll. Going for Warhammer's approach ("body" instead of "abdomen" and "chest") a d6 would suffice, otherwise we need a d8 to cover the seven possible locations. Of course that leaves another result we need to find a use for. Here is the first suggestion:<br />
<br />
<table style="text-align: center;">
<tbody>
<tr>
<th>Location</th><th>d6</th>
</tr>
<tr>
<td>Head</td><td>16.7% (1)</td>
</tr>
<tr>
<td>Right Arm</td><td>16.7% (2)</td>
</tr>
<tr>
<td>Left Arm</td><td>16.7% (3)</td>
</tr>
<tr>
<td>Body</td><td>16.7% (4)</td>
</tr>
<tr>
<td>Right Leg</td><td>16.7% (5)</td>
</tr>
<tr>
<td>Left Leg</td><td>16.7% (6)</td>
</tr>
</tbody></table>
<br />
Alright, not too bad. Of course I can already hear many of you complain that "head" is too frequent compared to "body" here, but that's simply the price we pay if we go for an even distribution. Here's the straightforward alternative:<br />
<br />
<table style="text-align: center;">
<tbody>
<tr>
<th>Location</th><th>d8</th>
</tr>
<tr>
<td>Head</td><td>12.5% (1)</td>
</tr>
<tr>
<td>Right Arm</td><td>12.5% (2)</td>
</tr>
<tr>
<td>Left Arm</td><td>12.5% (3)</td>
</tr>
<tr>
<td>Abdomen</td><td>12.5% (4)</td>
</tr>
<tr>
<td>Chest</td><td>12.5% (5)</td>
</tr>
<tr>
<td>Right Leg</td><td>12.5% (6)</td>
</tr>
<tr>
<td>Left Leg</td><td>12.5% (7)</td>
</tr>
<tr>
<td>?</td><td>12.5% (8)</td>
</tr>
</tbody></table>
<br />
What to do with the "leftover" result? Thinking ahead a bit, the location of an injury is actually not enough, we also need a measure of "severity" for the entire thing to work. So one option would be to assume that a "regular hit" just leaves a scar at the indicated location whereas rolling an 8 would indicate a more serious problem (re-roll to find the location). Another option would be to add another "location" of sorts, maybe "internal" or "systemic" injury?<br />
<br />
Now I have to admit that I already have a rough idea about the "severity" part, I'll probably make that some version of the <a href="http://nilisnotnull.blogspot.de/2014/11/riffing-on-2d6-reaction-rolls.html" target="_blank">2d6 reaction roll</a> eventually. With that in mind, the d8 version above seems less attractive: A different die to roll and that "leftover" category. So I have a feeling I'll end up with the d6 table using the Warhammer-style hit locations with a Legend-style distribution. (That's why I ended up calling this post "<i>Simple</i> Hit Locations" after all.) Opinions?Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com8tag:blogger.com,1999:blog-2240283907729630332.post-20037968387971358242015-12-31T11:45:00.000+01:002016-05-04T03:34:59.011+02:00Writing B/X Stuff with LaTeXA few weeks back I started rewriting my B/X house rules and I wanted to make things look <i>roughly</i> like the original B/X books. Note the roughly! I took some liberties with the original layout where it seemed appropriate.<br />
<br />
Then <a href="https://alexschroeder.ch/wiki/RPG" target="_blank">Alex Schroeder</a> said he'd maybe use such a LaTeX style as well, so I spent a few hours extracting things into a little LaTeX class file. Here's what documents formatted with <b>bxart</b> look like:<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://4.bp.blogspot.com/-DrCfMiBAwDs/VoUGbISCLPI/AAAAAAAAB10/r2Jcnd_5uXA/s1600/bxtest.jpg" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="640" src="https://4.bp.blogspot.com/-DrCfMiBAwDs/VoUGbISCLPI/AAAAAAAAB10/r2Jcnd_5uXA/s640/bxtest.jpg" width="494" /></a></div>
<br />
You can get the relevant files from my <a href="https://drive.google.com/folderview?id=0B5_s0vx_BCaGNmNOOEtRaFU2cjA&usp=sharing" target="_blank">Google Drive</a>. I am sure that this thing needs more work in the future, so I'll probably slap it on <a href="http://github.com/">github.com</a> sometime in 2016. Happy to hear your feedback!<br />
<br />
<b>Update 2016/05/03:</b> I've finally pushed this onto <a href="https://github.com/phf/latex-bx">github.com</a> so I am going to take down the Google Drive link to encourage folks to contribute. Of course to the best of my knowledge I only have one user anyway...Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com0tag:blogger.com,1999:blog-2240283907729630332.post-12581329547095979412015-12-30T15:53:00.000+01:002015-12-30T15:53:35.409+01:00Basement Delving: Tékumel<div class="firstHeading" id="firstHeading" lang="en">
In a very dark corner of my old basement I discovered a few of my <a href="https://en.wikipedia.org/wiki/T%C3%A9kumel">Tékumel</a> purchases from years ago. I have to admit that I never got very much into <a href="https://en.wikipedia.org/wiki/M._A._R._Barker">Professor Barker's</a> creation. Don't get me wrong, I always thought that his work was most impressive as far as I understood it. But I was very much distracted by the chaotic publication history of the darn thing: I could never really figure out which of the many books from all those many publishers is supposed to fit where. In any case, here's what I found:</div>
<div class="firstHeading" id="firstHeading" lang="en">
<br /></div>
<div class="separator" style="clear: both; text-align: center;">
<a href="http://2.bp.blogspot.com/-IQ9V2WflHfs/VoPkfHfxHdI/AAAAAAAAB0g/fSoj9zLEH_A/s1600/DSCN5800-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="400" src="http://2.bp.blogspot.com/-IQ9V2WflHfs/VoPkfHfxHdI/AAAAAAAAB0g/fSoj9zLEH_A/s400/DSCN5800-cut-color-small.JPG" width="300" /></a></div>
<br />
I don't know about you, but when I saw this thing in my FLGS back in the days, I just had to buy it. I mean come on, has there ever been a cooler looking RPG supplement? Ever? I just wish they had released a leather-bound hardcover written in actual blood! Even better, it had the following warning on the back:<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://3.bp.blogspot.com/-DEPVWUJAE8w/VoPkfte_aZI/AAAAAAAAB0k/VNxhWsOwmxQ/s1600/DSCN5801-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="240" src="http://3.bp.blogspot.com/-DEPVWUJAE8w/VoPkfte_aZI/AAAAAAAAB0k/VNxhWsOwmxQ/s320/DSCN5801-cut-color-small.JPG" width="320" /></a></div>
<br />
Not for children? Sorcerously explicit? Demons and shit? Very clever marketing indeed! I don't think I ever did more than flip through this thing, but I'll put it on my "should really be read soon" list now. The good professor even shows us what the "original" book looked like before he translated it into English:<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://1.bp.blogspot.com/-OTc1QD5y_LQ/VoPkgp_MJsI/AAAAAAAAB0w/aSA1HnaQ3Iw/s1600/DSCN5805-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="400" src="http://1.bp.blogspot.com/-OTc1QD5y_LQ/VoPkgp_MJsI/AAAAAAAAB0w/aSA1HnaQ3Iw/s400/DSCN5805-cut-color-small.JPG" width="300" /></a></div>
<br />
The language thing is after all the most obvious Barker-Tolkien connection. Barker's languages always seemed more exotic and scary to me, how very fitting for this particular book. Next we have what I think is the original Tékumel game system in the combined re-release from Different Worlds? But what do I know:<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://1.bp.blogspot.com/-SeDlb6oBeQ0/VoPkiG-nU3I/AAAAAAAAB08/Uk0jPEQgTg8/s1600/DSCN5807-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="400" src="http://1.bp.blogspot.com/-SeDlb6oBeQ0/VoPkiG-nU3I/AAAAAAAAB08/Uk0jPEQgTg8/s400/DSCN5807-cut-color-small.JPG" width="300" /></a></div>
<br />
And check out the cool "The Professor Approves" logo on the back! I wonder what Gygax's equivalent would have been? Presumably something a little less Playboy-like? I mean all he needs is a <a href="https://en.wikipedia.org/wiki/Smoking_jacket">smoking jacket</a>, right?<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://4.bp.blogspot.com/-2vwbxvYXfxQ/VoPkhWOZOUI/AAAAAAAAB00/B-nXNHdd_tc/s1600/DSCN5808-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="320" src="http://4.bp.blogspot.com/-2vwbxvYXfxQ/VoPkhWOZOUI/AAAAAAAAB00/B-nXNHdd_tc/s320/DSCN5808-cut-color-small.JPG" width="320" /></a></div>
<br />
Speaking of Gygax, the man himself actually wrote a Foreword to the original <a href="https://en.wikipedia.org/wiki/Empire_of_the_Petal_Throne">Empire of the Petal Throne</a> which is also included in this reprint:<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://4.bp.blogspot.com/-s1OcTcoWMrk/VoPknzoDgqI/AAAAAAAAB1I/7muQXlyH1q4/s1600/DSCN5809-cut-color-smallish.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="400" src="http://4.bp.blogspot.com/-s1OcTcoWMrk/VoPknzoDgqI/AAAAAAAAB1I/7muQXlyH1q4/s400/DSCN5809-cut-color-smallish.JPG" width="400" /></a></div>
<br />
I cannot tell how much of this is Gary being honest and how much of it is Gary being jealous. Maybe the truth is neither and it's really just a marketing blurb. The format of the book is quite curious, check out the table of contents:<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://4.bp.blogspot.com/-6PgALCEa2-c/VoPkoezjNQI/AAAAAAAAB1M/5J1knuGbTF0/s1600/DSCN5810-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="640" src="http://4.bp.blogspot.com/-6PgALCEa2-c/VoPkoezjNQI/AAAAAAAAB1M/5J1knuGbTF0/s640/DSCN5810-cut-color-small.JPG" width="480" /></a></div>
<br />
An interesting approach to numbering chapters and sections to say the least! Looks like a pretty complete system: character generation and advancement, combat, encounters and the underworld, magical items, gods and divine intervention... What's not to like? And hey, even a city is included (albeit not with a lot of detail):<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://1.bp.blogspot.com/-5PHS86ESp4g/VoPkoktWxZI/AAAAAAAAB1Q/mwzrTI0DI94/s1600/DSCN5811-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="300" src="http://1.bp.blogspot.com/-5PHS86ESp4g/VoPkoktWxZI/AAAAAAAAB1Q/mwzrTI0DI94/s400/DSCN5811-cut-color-small.JPG" width="400" /></a></div>
<br />
Finally one of the "newer" reincarnations of the game system, and honestly I have absolutely no idea why I bought this after already owning the version above:<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://4.bp.blogspot.com/-L_CE7zT9uE4/VoPkptDZJmI/AAAAAAAAB1g/bT3wpn9BUws/s1600/DSCN5813-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="400" src="http://4.bp.blogspot.com/-L_CE7zT9uE4/VoPkptDZJmI/AAAAAAAAB1g/bT3wpn9BUws/s400/DSCN5813-cut-color-small.JPG" width="300" /></a></div>
<div class="firstHeading" id="firstHeading" lang="en">
<br /></div>
<div class="firstHeading" id="firstHeading" lang="en">
I feel a little bit like <a href="https://alexschroeder.ch/wiki/2009-10-13_To_T%C3%A9kumel_Or_Not">Alex Schroeder</a> did back in 2009: Fascinated by the potential of this stuff, not entirely convinced that there's enough of a chance that I'll ever play it to dedicate more time to it. I am happy to give away the last one up there to someone who'll give it a good home, just email me if you're interested. I'll hang on to the other two for now hoping to find some bits and pieces to roll into my regular D&D gaming.</div>
Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com2tag:blogger.com,1999:blog-2240283907729630332.post-90869777900231078072015-12-30T14:06:00.001+01:002015-12-30T14:06:29.283+01:00Basement Delving: Thieves' GuildI have to admit that this post is mostly for me: I could never remember which of the various Thieves' Guild volumes I already had lying around in Germany, so I never ordered what I am missing from <a href="http://www.diffworlds.com/gamelords_thieves_guild.htm">Different Worlds</a>. Now I can finally complete my collection!<br />
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://3.bp.blogspot.com/-ehd26Ip3MrM/VoPUByWwjSI/AAAAAAAABz8/GgbSLIwNM0M/s1600/DSCN5759-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="320" src="http://3.bp.blogspot.com/-ehd26Ip3MrM/VoPUByWwjSI/AAAAAAAABz8/GgbSLIwNM0M/s320/DSCN5759-cut-color-small.JPG" width="240" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://2.bp.blogspot.com/-GY5XpmP0UoM/VoPUC_oYBUI/AAAAAAAAB0I/U23xyPjnqeo/s1600/DSCN5760-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="320" src="http://2.bp.blogspot.com/-GY5XpmP0UoM/VoPUC_oYBUI/AAAAAAAAB0I/U23xyPjnqeo/s320/DSCN5760-cut-color-small.JPG" width="240" /></a></div>
<br />
<div class="separator" style="clear: both; text-align: center;">
<a href="http://4.bp.blogspot.com/-fJBEE66tcdI/VoPUCWiXMSI/AAAAAAAAB0A/x8-jqh7bvDw/s1600/DSCN5763-cut-color-small.JPG" imageanchor="1" style="margin-left: 1em; margin-right: 1em;"><img border="0" height="320" src="http://4.bp.blogspot.com/-fJBEE66tcdI/VoPUCWiXMSI/AAAAAAAAB0A/x8-jqh7bvDw/s320/DSCN5763-cut-color-small.JPG" width="240" /></a></div>
<br />
I have a thing for the products that Gamelords Ltd. used to put out in the 1980s. The quality of most of their products is remarkably high although some of the "desktop publishing" from back then is pretty sad. (If someone gave me the raw text files I'd probably do a new layout for free!) <a href="http://heroworlds.blogspot.de/">Heroes and Other Worlds</a> has a <a href="http://heroworlds.blogspot.de/2014/03/retrospective-thieves-guid-and.html">fascinating article</a> (including further links) on Gamelords and Thieves' Guild as well.Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com0tag:blogger.com,1999:blog-2240283907729630332.post-78594751954568796022015-12-30T13:27:00.001+01:002015-12-30T13:27:36.986+01:00Basement Delving: War Cry and Battle LustI am in Germany again (yay!) so I can go into my old basement and hunt around for weird gaming crap that might be hiding down there. Today I found this little booklet between a whole bunch of other strange stuff I never actually played:<br />
<br />
<table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto; text-align: center;"><tbody>
<tr><td style="text-align: center;"><a href="http://1.bp.blogspot.com/-WyEuZ9VIKCE/VoPGBE9RSHI/AAAAAAAABzg/PANTyhU4uHA/s1600/DSCN5764-cut-color-small.JPG" imageanchor="1" style="margin-left: auto; margin-right: auto;"><img border="0" height="400" src="http://1.bp.blogspot.com/-WyEuZ9VIKCE/VoPGBE9RSHI/AAAAAAAABzg/PANTyhU4uHA/s400/DSCN5764-cut-color-small.JPG" width="300" /></a></td></tr>
<tr><td class="tr-caption" style="text-align: center;">War Cry and Battle Lust: Cover</td></tr>
</tbody></table>
<br />
As you might guess from the cover, this is a war game and not a role-playing game. On a quick browse it seems to be suitable for about the same kind of thing as <a href="https://en.wikipedia.org/wiki/Chainmail_%28game%29">Gygax and Perren's Chainmail</a>. Although War Cry came out seven years later (1978) it doesn't seem more advanced in any particular way. Better organized maybe? But of course I am hardly an expert on these kinds of games. Here are the combat tables (presumably the core of the game) from the center of the thin booklet:<br />
<br />
<table align="center" cellpadding="0" cellspacing="0" class="tr-caption-container" style="margin-left: auto; margin-right: auto; text-align: center;"><tbody>
<tr><td style="text-align: center;"><a href="http://3.bp.blogspot.com/-ePqaeYsCkuE/VoPGGpcNouI/AAAAAAAABzo/KYre4rZr0Ls/s1600/DSCN5767-cut-color-small.JPG" imageanchor="1" style="margin-left: auto; margin-right: auto;"><img border="0" height="400" src="http://3.bp.blogspot.com/-ePqaeYsCkuE/VoPGGpcNouI/AAAAAAAABzo/KYre4rZr0Ls/s400/DSCN5767-cut-color-small.JPG" width="300" /></a></td></tr>
<tr><td class="tr-caption" style="text-align: center;">War Cry and Battle Lust: Combat Tables</td></tr>
</tbody></table>
<br />
<a href="https://www.acaeum.com/">The Acaeum</a> reports (and the preface to the game admits this as well) that it's a very <a href="http://www.acaeum.com/jg/Item0068.html">streamlined system</a>: Maybe not overly realistic, but with reasonable outcomes and useful for resolving large battles more quickly than comparable systems.<br />
<br />
I'd love to hear from people who have used both Chainmail and War Cry. Sadly I won't have time for a thorough comparison myself, I am mired too deeply in the role-playing part of the hobby, just not enough interest in the war-gaming part. Hey, here's an idea: If you know Chainmail well and want to explore War Cry, I'll mail the darn thing to you for free. You just have to promise to write a blog post about how the games compare. Good deal?Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com1tag:blogger.com,1999:blog-2240283907729630332.post-77803957964517070412015-12-28T09:42:00.000+01:002015-12-28T09:42:48.074+01:00Exceptional B/X CharactersEnough about <a href="http://nilisnotnull.blogspot.de/2015/12/average-bx-characters.html">average characters</a>. We learned a bunch, but most of it was fairly obvious anyway. Let's talk briefly about <i>
exceptional </i>characters instead. Out of a million characters rolled up,
how many are exceptional? Well, what do we mean by exceptional? Maybe a
good approximation would be the total sum of all ability modifiers? For
simplicity let's just use the "standard" scale from -3 to +3 for all
abilities. Here are a few examples for "amazing" characters as well as the chance for rolling one:<br />
<br />
<table style="text-align: center;">
<tbody>
<tr>
<th>Class</th><th>S</th><th>I</th><th>W</th><th>D</th><th>C</th><th>X</th><th>Total</th><th>Chance</th>
</tr>
<tr>
<td>Cleric</td><td>15</td><td>16</td><td>18</td><td>12</td><td>16</td><td>18</td><td>+11</td><td>0.0001%</td>
</tr>
<tr>
<td>Fighter</td><td>18</td><td>11</td><td>16</td><td>17</td><td>14</td><td>18</td><td>+11</td><td>0.0002%</td>
</tr>
<tr>
<td>Magic-User</td><td>9</td><td>18</td><td>17</td><td>18</td><td>13</td><td>16</td><td>+11</td><td>0.0003%</td>
</tr>
<tr>
<td>Thief</td><td>18</td><td>10</td><td>15</td><td>18</td><td>16</td><td>13</td><td>+10</td><td>0.0016%</td>
</tr>
<tr>
<td>Dwarf</td><td>18</td><td>13</td><td>14</td><td>16</td><td>18</td><td>18</td><td>+13</td><td>0.0001%</td>
</tr>
<tr>
<td>Elf</td><td>18</td><td>18</td><td>14</td><td>14</td><td>18</td><td>15</td><td>+12</td><td>0.0001%</td>
</tr>
<tr>
<td>Halfling</td><td>18</td><td>13</td><td>17</td><td>16</td><td>18</td><td>15</td><td>+12</td><td>0.0002%</td>
</tr>
</tbody></table>
<br />
You may have guessed it, rolling up one of these monsters is basically impossible. The best result (certainly not a systemic issue, just a bunch of lucky rolls) is that 16 out of 1 million thieves are this awesome. That's not a lot, certainly not enough to ever actually see one of these characters in your games. But let's scale back a little bit: A character is pretty decent already if you get a total of +3 or more in terms of modifiers (and pretty bad if you get -3 or less) so what's the chance of rolling that? Better it turns out:<br />
<br />
<table style="text-align: center;">
<tbody>
<tr>
<th>Class</th><th>Chance >= +3</th><th>Chance <= -3</th>
</tr>
<tr>
<td>Cleric</td><td>11.65%</td><td>12.79%</td>
</tr>
<tr>
<td>Fighter</td><td>11.57%</td><td>12.75%</td>
</tr>
<tr>
<td>Magic-User</td><td>11.54%</td><td>12.79%</td>
</tr>
<tr>
<td>Thief</td><td>11.60%</td><td>12.75%</td>
</tr>
<tr>
<td>Dwarf</td><td>14.59%</td><td>8.05%</td>
</tr>
<tr>
<td>Elf</td><td>15.51%</td><td>8.33%</td>
</tr>
<tr>
<td>Halfling</td><td>19.53%</td><td>4.61%</td>
</tr>
</tbody></table>
<br />
It's a little surprising (for me anyway) that human characters have a better chance of being "bad" than "good" according to my simulation. Demi-human characters, on the other hand, have a better chance of turning out "good" as it were. Halflings are especially lucky in this regard, so maybe the next time you roll up a character who actually qualifies for being a Halfling, you should really go for one of those little buggers?<br />
<br />
(Sorry, I am sitting at my dad's weird Windoze box in Germany, so I don't have access to my usual Python toolbox of visualizations. I was going to plot the actual distributions for you, alas I'll have to add those things at a later date. I hope you still enjoyed reading what I have.)Peter Fröhlichhttp://www.blogger.com/profile/03688076015831464616noreply@blogger.com7