August 4, 2018

A Collection of Pearls as Well as Ever Sadder Epitaphs

Filed under: Open Sores — DianaComan @ 11:39 p.m.

Motto: Gura pacatosului, adevar graieste.

Deep inside the muck that passes for code among the open source tribes, there are pearls left not before the swine but rather plainly after them1. Like any pearls, they are the fruit of pain avoided and postponed, the signs of the beginning of defeat, the ever sadder epitaphs:

//@@@ Dirty, hack, this might be in a diffrent thread
//@@@ need to syncronize this in some way. But at least
//@@@ by moving this here the client code dosn't call
//@@@ SendOut anymore.

Oh, how truthful it starts, for it is indeed dirty and a hack and it "might be" something else "in some way" - that way being of course if only someone else wrote it! "But at least" it's written there and then never read or acted upon again of course, for how else would code be muck and shit accumulate at such tremendous speeds to make all those half a million lines of code?

 // REVERTED 3/8/03 Until I can figure out why this is causing client conencts to fail - Andrew Mann (Rhad)
// If we don't know who this connection is, don't handle ACKs
//if (!connection)
// return false;

It's 2018 and I'm sure he has figured it all out by now, right? The best way to figure things out is by avoiding them. Only for now, only a bit, only in "some way", only temporarily, of course. OF COURSE. And the best way to clean your house is by sweeping the dust under the carpet, don't you know?

// XXX: This is hacky, but we need to send the message to the client
// here and now! Because in the next moment he'll be deleted

"Where there is a need there is a right" or how did it go? The fact that you *need* to send a message in an ill-suited place at the wrong time to an idiot client and so on are ALL signs of problems to be sorted out not reasons for piling the shit higher and higher!

 // TODO: Hack, for now just get the y value and sector from the first point.

There, the great discovery of this year's lazy bums just as lazy as last year's lazy asses: don't do today what you can postpone indefinitely! And if it's on a todo list, then it doesn't need to actually be done! If I write that I'll do it then it's just as good as if I did it and way less work so it's win-win-me, isn't it? Especially since nobody will dare laugh at me for it since that's discrimination and a big no-no and I'll get all upset and they'll hurt my feelings.


This one truly reminds me of a children's story: a granny was once asked how many people were there at the party she had just attended. And she truthfully replied: only 1 person; for there was an old dirty barrel blocking the entrance and everyone got around it except for this last man who actually moved the barrel out of the way and only then got in.

What can I tell you, they used to teach this stuff in kindergarten!

 // Hack to work around the weird sector stuff we do.

This is the very way hacks reproduce until there is nothing left but a big pile of hacks precariously stacked on one another all the way to the moon. The hack because of the hack because of the hack because of the... Just stop hacking already and clean the darned shit from your house, you know? Why do you keep shitting where you eat?

// Special case for string, because we have to specify the namespace
// std::string, which doesn't play nicely with our FLAG__namespace hackery.

Hack and... counter-hack! If hacking breeding more hacking and shit growing up to your eyeballs wasn't already clearly and plainly the only result of this insanity. What does it take for you to stop this stupid approach with the special case for the extraordinary situation of the most unique item on the singularity of shit?

/* hack: if we included OpenSSL's ssl.h, we know about SSL_CTX
* this will of course break if we're included before OpenSSL headers...

You know it's broken but you ... do it anyway? The once inconceivable, the un-human, is that the modern human? Why, just why would anyone do such a thing knowingly?

/** @@@ Hack: please someone tell me how to do this better? */

Perhaps one of the saddest of them all: he is asking, you know? Perhaps in the wrong place, perhaps poorly stated, perhaps at the wrong moment, perhaps even only half-hearted but nevertheless... he asks for some guidance away from the swamps! But who answers, who is there to even read his comments at least if not his code? Of all the thousands pairs of eyes, none even blinks in recognition, not even once and the question remains there unanswered, the hack stays in place, the cry for help goes unheard and unnoticed for there is nobody to hear it. The thousands pairs of eyes stare without seeing anything for they are all little more than painted eyes on painted masks on painted cardboard in the painted world. Pure insanity this brave new world, the very stuff nightmares are made out of.

There truly is no worse loneliness than the loneliness of those trying to be people while lost among the crowds. For crowds are never, ever, people. And more importantly perhaps, out of necessity, crowds will always and invariably choose to mend and make do, just as reflected in all those comments above, never to clear away the rot that is left therefore to accumulate and fester and stink and drown everything. So next time *you* make your choice between the expensive exposure and fix of the rot on one hand and the mend and make do on the other, think perhaps also of that loneliness of the person in the crowd and of what it truly means to be - to become! - only one of the many, many identical pairs of unseeing eyes in the crowd.


  1. Hey, swine have rights too! What are you getting offended about? 

July 14, 2018

Cutting MySQL into Musl Shape

Filed under: Coding — DianaComan @ 3:40 p.m.

As I'm apparently the adventurous type or in fewer words an ice-breaker, I got to see all the ways in which MySQL fails to compile on a musltronic1 gentoo2. Note that there aren't that many versions of MySQL that portage knows about in the first place (exactly 5 versions: 5.5.60, 5.6.38, 5.6.39, 5.6.40, 5.7.22), mainly because of the nonsense proposition that "oh, we moved on to something new and shiny on which we got to stick another label and another name, be it mariadb". To quote specifically from mariadb itself when built3:

* Starting with version 10.1.8, MariaDB includes an improved systemd unit named mariadb.service
* You should prefer that unit over this package's mysqld.service.

Do you hear that? I won't even touch on the systemd nonsense but just read over and over again that part that says *you should prefer that unit* and nothing more. And tell me how can one write such a thing in the configuration files of a piece of software and then still have claim to ever be given the time of the day, not to mention to not being laughed out of town. And note that being laughed out of town is the best case there because frankly I find that offensive like hell rather than funny in the least.

Anyway, discarding with much pleasure the thing that "everyone" says I should prefer, here are the ways in which the various MySQL versions fail to emerge:

5.5.60: this version of MySQL pulls in openssl no matter what; even when libressl flag is added; even when -openssl is specifically added too; I just couldn't get it to leave openssl alone and so it's totally dead in the water. Not to mention that openssl then conflicts with libressl, so it's totally out of the question. RIP.

5.6.38: this was the preferred version so it was tried first, with a mask on anything greater than this aka >dev-db/mysql-5.6.38 written in /etc/portage/package.mask; it fails to compile because deep inside mysql code the stacktrace.c file relies on some thd_lib_detected variable and THD_LIB_LT constant to find out what implementation of threads it is running with. It was the first time I even saw those 2 things, a grep in MySQL code did NOT turn them anywhere else and then a quick dive into docs and everything else failed to find them anywhere *else* than in MySQL code. So I'm not even sure where are they meant to be set exactly, but given how the code compiles fine on a glibc system and fails miserably on the Musl system, I suspect it's some glibc-specific approach that got baked into this tiny corner of MySQL. Big mistake for the tiny corner, since the solution is to cut it away, of course. Anyway, the fail:

/var/tmp/portage/dev-db/mysql-5.6.38/work/mysql/mysys/stacktrace.c: In function 'my_print_stacktrace':
error: 'thd_lib_detected' undeclared (first use in this function)
sigreturn_frame_count = thd_lib_detected == THD_LIB_LT ? 2 : 1;
note: each undeclared identifier is reported only once for each function it appears in
error: 'THD_LIB_LT' undeclared (first use in this function)
sigreturn_frame_count = thd_lib_detected == THD_LIB_LT ? 2 : 1;

5.6.39: this is the version pulled by portage without any masking or keywords; it fails just like 5.6.38 with loud complaints about the unknown thd_lib constant & variable:

error: 'thd_lib_detected' undeclared (first use in this function)
sigreturn_frame_count = thd_lib_detected == THD_LIB_LT ? 2 : 1;
note: each undeclared identifier is reported only once for each function it appears in
error: 'THD_LIB_LT' undeclared (first use in this function)
sigreturn_frame_count = thd_lib_detected == THD_LIB_LT ? 2 : 1;

5.6.40: this fails quite the same as the 5.6.38 and 5.6.49 above:

/var/tmp/portage/dev-db/mysql-5.6.40/work/mysql/mysys/stacktrace.c: In function 'my_print_stacktrace':
error: 'thd_lib_detected' undeclared (first use in this function)
sigreturn_frame_count = thd_lib_detected == THD_LIB_LT ? 2 : 1;
note: each undeclared identifier is reported only once for each function it appears in
error: 'THD_LIB_LT' undeclared (first use in this function)
sigreturn_frame_count = thd_lib_detected == THD_LIB_LT ? 2 : 1;

5.7.22: this version requires the ~amd64 keywords on my proto-cuntoo so it's supposedly "at your own risk" grade. It fails at configuration stage with CMake barfing about a lack of mysys timer:

CMake Error at configure.cmake:573 (MESSAGE):
No mysys timer support detected!
Call Stack (most recent call first):
CMakeLists.txt:451 (INCLUDE)

And then I threw my hands up in despair at it all, took the plunge into MySQL code and Gentoo's very useful ebuild command4, cut away the misbehaving part and had the pleasant surprise that it was actually enough to make the whole thing work! After which I spent of course another few hours just checking the whole thing through because by now I am very, very suspicious when it's relatively easy to fix something.

The good news is that MySQL can be made to work on a musltronic system with just a small snip of the "safe printing" of a stacktrace - as I'm not terribly concerned at this time about MySQL's own stacktrace printing, I didn't really spend the time to *fix* the code although I'm sure it can be done with a bit of study of threads in Musl. For now though I am content to just delete that code and yes, have a MySQL that won't print its stacktrace. Specifically, here are the steps to get MySQL going on a proto-cuntoo system:

1. Get the source code by instructing ebuild to "fetch":

ebuild /usr/portage/dev-db/mysql/mysql-5.6.38.ebuild fetch

2. Unpack it:

ebuild /usr/portage/dev-db/mysql/mysql-5.6.38.ebuild unpack

3. Simply delete the contents of method my_print_stacktrace(uchar* stack_bottom, ulong thread_stack)  in /var/tmp/portage/dev-db/mysql-5.6.39/work/mysql/mysys/stacktrace.c and save the file. Leave the empty shell of the method there since it IS called (yes, I checked). Ideally one would fix the code I guess, but atm I really don't see this worth the time since the moment mysql fails that badly I seriously doubt I'll want to spend the time investigating its stack trace - it's more likely I'll throw it out the window entirely. At any rate, as this is not a "fix" by any measure, I'm not making it into a patch so you'll have to run through those steps rather than just emerge.

4. With the code thus modified, ask ebuild to go ahead and compile, install and then merge the result into the live file system, so three different commands to be run one at a time:

ebuild /usr/portage/dev-db/mysql/mysql-5.6.38.ebuild compile
ebuild /usr/portage/dev-db/mysql/mysql-5.6.38.ebuild install
ebuild /usr/portage/dev-db/mysql/mysql-5.6.38.ebuild qmerge

5. It's done; run your usual emerge --config=dev-db/mysql-5.6.38 and set the root password, create databases and users, as you need.

And there it is, I can happily report that MySQL 5.6.38 is now compiling and running quite happily on a fully musltronic system!

  1. Aka Musl-based rather than glibc-inflated. 

  2. Also known as proto-cuntoo since that's exactly what it is: an alpha version of trinque's cuntoo.  

  3. Yes, I built this one too and it builds fine. No, I won't use it though. 

  4. Man page for ebuild most recommended read! 

July 10, 2018

Some Branching Troubles on Existing V Trees

Filed under: Coding — DianaComan @ 10:03 p.m.

In theory - when there IS a theory! - everything is neat, simple and takes almost no time1. Today's everything started similarly neat and simple with a clear goal that was not meant to take much time: finding a better home for my Keccak implementation.

To clarify the issue here: currently Keccak is part of EuCrypt mainly because at the time of its implementation there simply was no better place for it. But meanwhile phf integrated Keccak into his vtools, esthlos is actively searching for the best way to use Keccak hashes as part of his own V implementation and Arjen (ave1) has released a zero foot print (ZFP) library that is delightfully effective at eliminating bloat. And on top of all this, V itself is moving forward with more clarity and better practices: there shall be a manifest file, there shall be Keccak hashes instead of sha512. Combined, all those developments really point and prod at the simple fact: Keccak both needs and can get a better home now - namely a home as a branch off ave1's zfp tree!

Branching off an existing V tree is meant to be a straightforward task: press the original tree to the desired leaf, add SMG.Keccak, produce new patch, test that it sits indeed at desired place in the tree and it presses fine, write it all up, release and enjoy. But it didn't take long to get into trouble:

  1. To start with, it turned out that current Keccak can not yet use ZFP because its OAEP wrapper requires Interfaces.C and ZFP does not yet support it. Nevertheless, this is noted and added to the README next to the code but it's not in itself a game stopper: the runtime library to be used is anyway specified with the --RTS switch when invoking gprbuild so there is no need to change anything at a later time when ZFP supports Interfaces.C; moreover, the OAEP wrapper is really just a convenience wrapper so it can be removed if the user desires a stripped down pure Keccak in Ada.
  2. Then, vtools and v.pl seemed to not want to play nice together and they sputtered all sorts - this was the easy part to solve though as it turned out I had forgotten to chop the vtools branches properly and keep only one set of patches. Thanks to spyked and phf (and via the logs of course), the needed jolt to my memory was provided, the previous log discussion found and linked, the problem solved: as a result, I had again (as I even remembered I used to have at some other point) the spiffy2 vtools working smoothly and producing the desired Keccak-hashed vpatch.
  3. And then it turned out that I can't quite attach my shiny new vpatch to ave1's tree because my vpatch uses Keccak hashes while his other vpatches are still using sha512 and the combination is of course rather unsanitary.
  4. Adding to the above, I also have quite some trouble in finding a way to properly attach my Keccak patch to the current leaf in ave1's simple tree. Since there isn't a manifest file, I can't take the easy route of not even worrying about this issue and simply add the corresponding line for my patch to this file, knowing it'll come neatly after the current leaf. And it turns out that the difficult solution of making sure I change some file changed by the current leaf is also rather dubious because zfp_2_noc.vpatch changes only a few code files that Keccak really has NO business whatsoever in touching *at all*.
  5. A relatively minor issue by comparison with the ones above but still promising to give headache in the future is the fact that current zfp doesn't actually have its own top directory. So where exactly should I plonk smg_keccak folder in there?

What can I do?

  1. There's a reason many people like theories, especially at a safe distance from practice. 

  2. It's Stanislav's term but it fits best here! 

June 26, 2018

Eulora's Own CR50

Filed under: Eulora — DianaComan @ 9:29 p.m.

Possibly similar to the CR50 item Stanislav has been torturing recently, a green "Microchip" of unknown internals and dubious usefulness has finally been teased out of the reluctant and downright hostile Euloran soil. It took only a bit more than 3 years of pounding said soil.

On the plus side, it seems to be quite valuable at somewhere around 110`000 ECu (aka 11`000 satoshi atm) base value. On the more usual *other* side, there is no known use for it at the moment1 and it came out very low quality too, not to mention potentially booby trapped for all one knows:

Eulora's own CR50! Microchip!!1

The floating Microchips!

At any rate, I hereby dedicate this very first lot of Microchips to Stanislav Datskovskiy. May all his quests be successful and take considerably less than it took me to find this item!

  1. It wasn't needed until now, which is of course "no indication of future performance". 

June 15, 2018

EuCrypt Manifest File

Filed under: EuCrypt — DianaComan @ 2:09 p.m.

~ This is part of the EuCrypt series. Start with Introducing EuCrypt. ~

This little patch simply adds a manifest file to EuCrypt so that the intended order of patches is made explicit, easily accessible and easily maintained throughout the life of the project even as new patches are added by others (hopefully). I've created this file following the manifest format specification proposed by Michael Trinque. For each patch, I used the block count1 as reported by mimisbrunnr on the day when I published the patch.

Since I publish this as a .vpatch on top of existing EuCrypt itself, there is of course a line in the manifest file for this vpatch too. To keep it nicely flowing from the previous last leaf of EuCrypt, there is an additonal change to the README file of the project as well (since it's this file I have used so far, before the manifest solution was adopted, as an implicit way of forcing some meaningful order on the vpatches).

As usual, the .vpatch and its signatures can be found on my Reference Code Shelf and are also linked directly from here for your convenience:

  1. Starting with last round number on that day so as to have some space for the case when there were several patches on same day. 

June 10, 2018

Chasing the Elusive Euloran Quality

Filed under: Eulora — DianaComan @ 3:45 p.m.

Quality of items in Eulora is a big thing - it brings in more money for whoever can deliver it and it also gives one better dings. Or at least better chances at better dings1, it would seem. Welcome to the murky shores of Eulora, this land open to all and totally opaque to most2.

The most recent update3 was cheered for finally making it possible to actually do expensive stuff in a few minutes as opposed to a few months. After which there was silence and renewed confusion as to what is what and how much any darned thing is worth. Quite a lot of discussion ensued in the #eulora irc chan although mainly between me and Mircea Popescu as the rest of the veteran players4 seem to either have no clue or have no appetite for talking at this stage. Hopefully they'll find one if not both at some later point before totally sinking out of sight, unknown and unmissed for lack of actually being there, who knows.

While discussions in logs are all fine and good, they tend to be difficult to find and retrieve at a later time. So for my own future needs and potentially for others' use, I'd rather jot down here a few data points on all this. The most recent problem is that apparently *everything* works now as a quality sink: mining eats up crafted items of 4k quality to give back harvestables at 900q while crafting wants also to eat harvestables at 900q to possibly give something back at all (not even clear if >900q, at that; a reported craft that "almost works" brings down q from 90 to 84). After all sorts of experiments with my team of noob and not-so-noob helpers, I suggested that people might simply be approaching the issue here from the wrong end, a sort of trying to dig their way out of the hole instead of making a ladder to climb back up. I know that a big-enough dig can indeed get one out of any hole through the other side, but Eulora's rather short on shovels at this very moment5. So how about that ladder then? It starts with more experimenting and concrete data, such as this, collected over only a few crafting runs of Slag (base value 677):


Tinkering Rank Sortage Rank Blueprint Quality Bundle Quality Output
1265 448 133 664 0 Slag + TPF q401
1265 448 67 664 0 Slag + TPF q285
1265 448 1 664 4-5 Slag + TPF q32
245 77 133 664 2 Slag q213 +TPF
245 77 67 664 3 Slag q151 + TPF
74 67 133 664 2 Slag q198 + TPF
74 67 67 664 4 Slag q141 + TPF

All the runs had remarkably similar results (same quality always, same number of slag items always except where it appears in table as 4-5 i.e. sometimes 4, sometimes 5) so I simply recorded one result for each combination. The bundles there are all identical and made by the highest skilled crafter as she can pack most value into the bundle. Specifically, each bundle is made out of 17 Flotsam q192 and 11 Shiny Rock 187q. For one thing, this suggests that the highest crafter packs the ingredients for almost 4 slags into one single bundle. For the other, it means that any output < 190q is anyway a sink of quality, no matter how one looks at it. And looking at it, there is some support on both points: 4 slags are reliably obtained by highest skilled crafter with a blueprint of lowest quality possible, 1. They are however q32 meaning that quality was severely lost in the process. When quality is not lost by the highest skilled crafter, it is however totally transfered to numina it would seem: all output is numina and no slag at all.

Considering the results of the other two crafters, the most interesting part is that they can actually get Slag of higher quality than the inputs that went in: for the same ~q190 harvestables used as input, they get reliably outputs >q150, even close to q200 in one combination! So for one thing it's certainly NOT true that crafting is a sink of quality, quite on the contrary: it clearly creates quality of output - the only trouble is however to match the sort of output one wants (i.e. product not so much numina at the moment).

The even more interesting bit suggested by this teeny tiny amount of data is with respect to just how much of the actual value going in is then obtained back as Slag rather than numina. The input value is roughly 677*6.64 = 4495 ignoring the value of the blueprint (which is not much at 67*1.33 maximum in there). Highly skilled crafter gets precisely 0 in Slag out of this and all of it in numina unless they go for low quality when they get between 4*677*0.32=866 and 5*677*0.32=1083 so anyway about a quarter maximum. By contrast, middle level crafter gets 2*677*2.13=2884 or 3*677*1.51=3066 at lower quality so about 70% of the input value. And lower level crafter gets even more at their lower quality 4*677*1.41=3818 (or 2*677*1.98=2680 for their higher quality).

Before jumping to any conclusions, I'll add that I'm quite sure that the data captured there (i.e. Tinkering and Sortage skill ranks, blueprint quality, bundle quality, item) is quite unlikely to really capture ALL factors that influence the outcome. For one thing I can tell for instance from long experience with those characters involved that the highest skilled crafter tends to be rather unlucky in everything she does, while the middle skilled crafter tends to be quite the opposite - lucky and then some more.

With the above caveats in mind and other potential limitations quite obvious6, a conclusion is to be drawn and that is that at least on such low base value items beginner and middle level crafters are actually in a very good position to bump up quality and make a killing - if only they do buy the bundles of a highly skilled crafter! In turn, their output is likely to actually help highly skilled crafters as it gives them more quality as input for more valuable crafts presumably.

As for the highly skilled crafter, it would seem to me that she would really need to somehow pack in at least 4 times the value of Slag at her output quality of 401 in order to stand a chance of getting q401 Slag. That means she needs a bundle of 4*677*4.01=10859 so about 3 times more than what she made for this little experiment. Either she gets that from an even higher crafter (who can pack more of same q harvestables into one bundle) or she uses harvestables at quality at least 600 by the looks of it. Good luck with that my lovely, as q600 harvestables will come at a hefty premium at least from my wares - if they even come at all as it's not all that clear at this moment that such stocks can be replenished if used!

Other than that: isn't it marvelous how much one can get even from only a few numbers? If only they do bother to get those numbers in the first place, of course...

  1. The term of art in Eulora is "pop" as in "1002mn pop, wow!" i.e. you put in 10mn and got 1002mn out of it, you lucky bastard. 

  2. That post was written in 2015, yes. Not much changed since then in terms of players' understanding of Eulora's actual workings it would seem. Poor Eulora, so totally incomprehensible, so entirely misunderstood... 

  3. 'Tis not even by far the only update Eulora went through so far. And all updates introduce changes that so far seem to mess up players' previous plans something fierce. 

  4. Noobs have yet some other things to figure out before standing much chance with this really. 

  5. And since I'm not that young anymore in Eulora either, I can tell you that I've subsidized this sort of approach at least once before and I don't want to do it again, ever. It was costly, very very costly. 

  6. Very small sample is the most obvious but you really are better off thinking for yourself on this. 

June 5, 2018

The Lack of Dust - A Very Euloran Problem

Filed under: Eulora — DianaComan @ 6:23 p.m.

Collected Dusts in Eulora are a thing - a very useful and currently very much required thing. Consequently, according to the usual Euloran workings, Collected Dusts are also... rather sorely needed and totally missing from the market. In other words, Collected Dusts are hard to get, needed by the ton, while also unknown as to actual value - the usual stuff. And so Foxy set up to... get those1, since she is anyway best at Lapidary2.

At first, the recent update seemed as if it might help for once - first level numina such as Dusts are normally obtained as a byproduct of crafting in the respective line. That would mean that one gets tons of Dusts simply by clicking something in the Bouquinism line. And that is... true of sorts but the trouble is that Bouquinism is a bit special and most of its items give stuff-other-than-numina (blueprints mostly). Moreover, while the recent update seems to have turned skilled crafters' clicks into mainly-numina-producing clicks, this does not really hold for Bouquinism! Click on Maculature and instead of loads of Dusts, one still gets loads of... Little Bits O' Nothing. What do?

Well, whenever the rule doesn't work, one needs to find... the exception, of course. For various definitions of find that might involve workarounds and workthroughs and workaboves and workbeyonds and workinbetweens - more generally speaking: WORK. So work it is then, onwards! In this case the work is mainly to figure out how to make mites in large quantities through lots of smaller clicks since apparently I don't have enough input stuff to get more than a few mites through huge-quality single click sort of thing.

First, I tried all sorts of combination-clicking on Maculature in the vain hope that Bouquinism might still sort-of-work like the rest and spit some Dusts: high q bundle with total noob -> ton of LBN (Little Bits O' Nothing) and nothing else; high q bundle with high q bp (recipe) and Foxy's click -> ton of Nothing just the same; you name it, I tried it -> no, nope and nono.

Second, I made then some Bird's Nest and Gin, poured it over that WPL3 that nobody wanted yesterday but wanted today4. That made the ECV5 in tiny quantities and ...DUSTS! In... some quantities because on one hand I did get a few thousands of them but on the other hand Foxy needs at least 3300 for one single Lapidary click that makes usually only about 20-30 Mites so by this measure... still totally and utterly stuck (and no, making some million of Bird's Nest and Gin is not a useful "solution"). What do?

Third, I got a total noob to look at Foxy's Toil recipes (the ones that make Mites out of Dusts). And what do you know? Noob can make a bundle with one single Dust and one single WOA (Water of Anamnesia - another thing that seems to be rather wanted and in short supply at the moment). So noob was set with the bundling bot to make a few hundred bundles that came out an actually reasonable ~1300 quality because Foxy's Dusts are high quality and Foxy's ancient WOA are ALSO high quality. Wonderful, except for a teeny tiny problem: clicking a 1300 quality bundle with a high quality Toil bp seems to end up for Foxy in... no Mites, only Gem Dusts (Lapidary numina). On the other hand, clicking it with the noob gets Mites, but poor, sickly and stinky ones - frightfully low quality, not to mention basically wasting all that Lapidary experience on the unsuspecting noob. Once again: WHAT do?

Fourth, got the big mixing guns out of Foxybot: blueprint quality doesn't have to be huge if one also has6 quality 1 blueprints of the same type! Some many clicks and 2000 mixings later, there we go, found some sort of combination that works! Foxy reliably gets at least 10 mites per click - not to mention many more when she pops or mini-pops - at a quality above 500 and she has *hundreds* of bundles and blueprints to click right now!

And the cherry on the above delightful cake is that it takes only 2 of those clicks for Foxy to rank up in Lapidary. Combined with the bot's powerful crafting-with-bundle7, she basically got 100 ranks up in one hour today and scooped up the book-prize for being first to reach 600 rank in Lapidary!

Onwards and upwards, let's reach that 800 Lapidary before tomorrow's update 'cause I'll be busy mining: there are new problems to solve, troubles to find and generally millions of coins waiting to be picked up, scooped out, teased away from Eulora! If only, of course... you actually work at knowing how to do such a feat. Do you?

  1. By now I can say I have a thing for... prickly problems let's call them, what can I do. 

  2. The crafting line that works on numina such as Dusts, transforming it from lower levels to higher levels (e.g. from Dusts to Mites and so on). 

  3. Worthless Putrid Leather 

  4. Ha, HA! 

  5. Extremely Creaky Vellum 

  6. by means of previous noob-clicking, at another time, there's nothing totally useless if only done correctly in Eulora, you know? 

  7. No, you don't have this working anymore? Awww. The help and the code have been there for ages, waiting for... you . Where have you been? 

June 4, 2018

Rocking Fuckgoats on the Rock-chip

Filed under: Coding — DianaComan @ 2:27 p.m.

My very own gem-like Rockchip machine leased from the very friendly Pizarro1 comes of course with an excellent Fuckgoat source of randomness from my favourite hardware producer, No Such Labs. How else would it even really qualify as a useful computer without access to at least one FG? And since this Rockchip is more or less a testing ground of all sorts for me and for now, here are the results of 3 test-runs (ent and dieharder applied to 3 different 3.0G files of FG output):

Run 1
ent output:

Entropy = 8.000000 bits per byte.

Optimum compression would reduce the size
of this 3145728000 byte file by 0 percent.

Chi square distribution for 3145728000 samples is 301.70, and randomly
would exceed this value 2.37 percent of the times.

Arithmetic mean value of data bytes is 127.5014 (127.5 = random).
Monte Carlo value for Pi is 3.141654373 (error 0.00 percent).
Serial correlation coefficient is 0.000020 (totally uncorrelated = 0.0).

dieharder output:

#            dieharder version 3.31.1 Copyright 2003 Robert G. Brown          #
   rng_name    |           filename             |rands/second|
 file_input_raw|                         fg1.bin|  5.55e+06  |
        test_name   |ntup| tsamples |psamples|  p-value |Assessment
   diehard_birthdays|   0|       100|     100|0.55364402|  PASSED
      diehard_operm5|   0|   1000000|     100|0.77308483|  PASSED
  diehard_rank_32x32|   0|     40000|     100|0.39821868|  PASSED
    diehard_rank_6x8|   0|    100000|     100|0.43441145|  PASSED
   diehard_bitstream|   0|   2097152|     100|0.24694838|  PASSED
        diehard_opso|   0|   2097152|     100|0.79287254|  PASSED
        diehard_oqso|   0|   2097152|     100|0.10727946|  PASSED
         diehard_dna|   0|   2097152|     100|0.71618516|  PASSED
diehard_count_1s_str|   0|    256000|     100|0.14310424|  PASSED
diehard_count_1s_byt|   0|    256000|     100|0.06331660|  PASSED
 diehard_parking_lot|   0|     12000|     100|0.07270933|  PASSED
    diehard_2dsphere|   2|      8000|     100|0.55501201|  PASSED
    diehard_3dsphere|   3|      4000|     100|0.14071812|  PASSED
     diehard_squeeze|   0|    100000|     100|0.72435262|  PASSED
        diehard_sums|   0|       100|     100|0.52920652|  PASSED
        diehard_runs|   0|    100000|     100|0.71532176|  PASSED
        diehard_runs|   0|    100000|     100|0.04142495|  PASSED
       diehard_craps|   0|    200000|     100|0.60495179|  PASSED
       diehard_craps|   0|    200000|     100|0.13140280|  PASSED
 marsaglia_tsang_gcd|   0|  10000000|     100|0.98053930|  PASSED
 marsaglia_tsang_gcd|   0|  10000000|     100|0.30154457|  PASSED
         sts_monobit|   1|    100000|     100|0.70277769|  PASSED
            sts_runs|   2|    100000|     100|0.72995953|  PASSED
          sts_serial|   1|    100000|     100|0.07480821|  PASSED
          sts_serial|   2|    100000|     100|0.43219474|  PASSED
          sts_serial|   3|    100000|     100|0.95572839|  PASSED
          sts_serial|   3|    100000|     100|0.05183212|  PASSED
          sts_serial|   4|    100000|     100|0.86243828|  PASSED
          sts_serial|   4|    100000|     100|0.54979184|  PASSED
          sts_serial|   5|    100000|     100|0.99943852|   WEAK
          sts_serial|   5|    100000|     100|0.98416336|  PASSED
          sts_serial|   6|    100000|     100|0.41224989|  PASSED
          sts_serial|   6|    100000|     100|0.23138405|  PASSED
          sts_serial|   7|    100000|     100|0.37811898|  PASSED
          sts_serial|   7|    100000|     100|0.68995575|  PASSED
          sts_serial|   8|    100000|     100|0.32399498|  PASSED
          sts_serial|   8|    100000|     100|0.68248678|  PASSED
          sts_serial|   9|    100000|     100|0.52331440|  PASSED
          sts_serial|   9|    100000|     100|0.61259715|  PASSED
          sts_serial|  10|    100000|     100|0.40033877|  PASSED
          sts_serial|  10|    100000|     100|0.84566398|  PASSED
          sts_serial|  11|    100000|     100|0.48551729|  PASSED
          sts_serial|  11|    100000|     100|0.63831521|  PASSED
          sts_serial|  12|    100000|     100|0.77176883|  PASSED
          sts_serial|  12|    100000|     100|0.77784212|  PASSED
          sts_serial|  13|    100000|     100|0.93553942|  PASSED
          sts_serial|  13|    100000|     100|0.33559759|  PASSED
          sts_serial|  14|    100000|     100|0.27845394|  PASSED
          sts_serial|  14|    100000|     100|0.26469467|  PASSED
          sts_serial|  15|    100000|     100|0.94553460|  PASSED
          sts_serial|  15|    100000|     100|0.86955787|  PASSED
          sts_serial|  16|    100000|     100|0.52513415|  PASSED
          sts_serial|  16|    100000|     100|0.75823923|  PASSED
         rgb_bitdist|   1|    100000|     100|0.93155438|  PASSED
         rgb_bitdist|   2|    100000|     100|0.81178456|  PASSED
         rgb_bitdist|   3|    100000|     100|0.96463454|  PASSED
         rgb_bitdist|   4|    100000|     100|0.25858769|  PASSED
         rgb_bitdist|   5|    100000|     100|0.87115232|  PASSED
         rgb_bitdist|   6|    100000|     100|0.32606816|  PASSED
         rgb_bitdist|   7|    100000|     100|0.06276018|  PASSED
         rgb_bitdist|   8|    100000|     100|0.80690784|  PASSED
         rgb_bitdist|   9|    100000|     100|0.43129323|  PASSED
         rgb_bitdist|  10|    100000|     100|0.26529646|  PASSED
         rgb_bitdist|  11|    100000|     100|0.83773896|  PASSED
         rgb_bitdist|  12|    100000|     100|0.76575354|  PASSED
rgb_minimum_distance|   2|     10000|    1000|0.25694562|  PASSED
rgb_minimum_distance|   3|     10000|    1000|0.01512658|  PASSED
rgb_minimum_distance|   4|     10000|    1000|0.57060500|  PASSED
rgb_minimum_distance|   5|     10000|    1000|0.49218844|  PASSED
    rgb_permutations|   2|    100000|     100|0.29144608|  PASSED
    rgb_permutations|   3|    100000|     100|0.15806101|  PASSED
    rgb_permutations|   4|    100000|     100|0.28135408|  PASSED
    rgb_permutations|   5|    100000|     100|0.50106116|  PASSED
      rgb_lagged_sum|   0|   1000000|     100|0.11294777|  PASSED
      rgb_lagged_sum|   1|   1000000|     100|0.97600408|  PASSED
      rgb_lagged_sum|   2|   1000000|     100|0.88053766|  PASSED
      rgb_lagged_sum|   3|   1000000|     100|0.64089472|  PASSED
      rgb_lagged_sum|   4|   1000000|     100|0.40792228|  PASSED
      rgb_lagged_sum|   5|   1000000|     100|0.96756087|  PASSED
      rgb_lagged_sum|   6|   1000000|     100|0.65817930|  PASSED
      rgb_lagged_sum|   7|   1000000|     100|0.43277428|  PASSED
      rgb_lagged_sum|   8|   1000000|     100|0.44916686|  PASSED
      rgb_lagged_sum|   9|   1000000|     100|0.35982130|  PASSED
      rgb_lagged_sum|  10|   1000000|     100|0.29814491|  PASSED
      rgb_lagged_sum|  11|   1000000|     100|0.46604337|  PASSED
      rgb_lagged_sum|  12|   1000000|     100|0.88106085|  PASSED
      rgb_lagged_sum|  13|   1000000|     100|0.42486184|  PASSED
      rgb_lagged_sum|  14|   1000000|     100|0.08230131|  PASSED
      rgb_lagged_sum|  15|   1000000|     100|0.26067988|  PASSED
      rgb_lagged_sum|  16|   1000000|     100|0.28780477|  PASSED
      rgb_lagged_sum|  17|   1000000|     100|0.73099818|  PASSED
      rgb_lagged_sum|  18|   1000000|     100|0.14950848|  PASSED
      rgb_lagged_sum|  19|   1000000|     100|0.73904147|  PASSED
      rgb_lagged_sum|  20|   1000000|     100|0.22744739|  PASSED
      rgb_lagged_sum|  21|   1000000|     100|0.23185584|  PASSED
      rgb_lagged_sum|  22|   1000000|     100|0.42494100|  PASSED
      rgb_lagged_sum|  23|   1000000|     100|0.03097538|  PASSED
      rgb_lagged_sum|  24|   1000000|     100|0.02973134|  PASSED
      rgb_lagged_sum|  25|   1000000|     100|0.44057431|  PASSED
      rgb_lagged_sum|  26|   1000000|     100|0.64997314|  PASSED
      rgb_lagged_sum|  27|   1000000|     100|0.75063931|  PASSED
      rgb_lagged_sum|  28|   1000000|     100|0.85409468|  PASSED
      rgb_lagged_sum|  29|   1000000|     100|0.00025354|   WEAK
      rgb_lagged_sum|  30|   1000000|     100|0.36725989|  PASSED
      rgb_lagged_sum|  31|   1000000|     100|0.24486715|  PASSED
      rgb_lagged_sum|  32|   1000000|     100|0.27217099|  PASSED
     rgb_kstest_test|   0|     10000|    1000|0.18178764|  PASSED
     dab_bytedistrib|   0|  51200000|       1|0.75375432|  PASSED
             dab_dct| 256|     50000|       1|0.18116969|  PASSED
Preparing to run test 207.  ntuple = 0
        dab_filltree|  32|  15000000|       1|0.98519789|  PASSED
        dab_filltree|  32|  15000000|       1|0.88193954|  PASSED
Preparing to run test 208.  ntuple = 0
       dab_filltree2|   0|   5000000|       1|0.20211019|  PASSED
       dab_filltree2|   1|   5000000|       1|0.15789329|  PASSED
Preparing to run test 209.  ntuple = 0
        dab_monobit2|  12|  65000000|       1|0.79929581|  PASSED

Run 2
ent output:

Entropy = 8.000000 bits per byte.

Optimum compression would reduce the size
of this 3145728000 byte file by 0 percent.

Chi square distribution for 3145728000 samples is 202.01, and randomly
would exceed this value 99.38 percent of the times.

Arithmetic mean value of data bytes is 127.5008 (127.5 = random).
Monte Carlo value for Pi is 3.141640625 (error 0.00 percent).
Serial correlation coefficient is 0.000001 (totally uncorrelated = 0.0).

dieharder output:

#            dieharder version 3.31.1 Copyright 2003 Robert G. Brown          #
   rng_name    |           filename             |rands/second|
 file_input_raw|                         fg2.bin|  5.64e+06  |
        test_name   |ntup| tsamples |psamples|  p-value |Assessment
   diehard_birthdays|   0|       100|     100|0.02763152|  PASSED
      diehard_operm5|   0|   1000000|     100|0.92568798|  PASSED
  diehard_rank_32x32|   0|     40000|     100|0.73663405|  PASSED
    diehard_rank_6x8|   0|    100000|     100|0.78211683|  PASSED
   diehard_bitstream|   0|   2097152|     100|0.05716587|  PASSED
        diehard_opso|   0|   2097152|     100|0.26951494|  PASSED
        diehard_oqso|   0|   2097152|     100|0.12410320|  PASSED
         diehard_dna|   0|   2097152|     100|0.24763351|  PASSED
diehard_count_1s_str|   0|    256000|     100|0.25380539|  PASSED
diehard_count_1s_byt|   0|    256000|     100|0.46545254|  PASSED
 diehard_parking_lot|   0|     12000|     100|0.07295537|  PASSED
    diehard_2dsphere|   2|      8000|     100|0.15111149|  PASSED
    diehard_3dsphere|   3|      4000|     100|0.18263229|  PASSED
     diehard_squeeze|   0|    100000|     100|0.00869371|  PASSED
        diehard_sums|   0|       100|     100|0.15403389|  PASSED
        diehard_runs|   0|    100000|     100|0.80060735|  PASSED
        diehard_runs|   0|    100000|     100|0.51712024|  PASSED
       diehard_craps|   0|    200000|     100|0.85163527|  PASSED
       diehard_craps|   0|    200000|     100|0.06273509|  PASSED
 marsaglia_tsang_gcd|   0|  10000000|     100|0.85142564|  PASSED
 marsaglia_tsang_gcd|   0|  10000000|     100|0.65731674|  PASSED
         sts_monobit|   1|    100000|     100|0.52436851|  PASSED
            sts_runs|   2|    100000|     100|0.52338059|  PASSED
          sts_serial|   1|    100000|     100|0.41493433|  PASSED
          sts_serial|   2|    100000|     100|0.37546843|  PASSED
          sts_serial|   3|    100000|     100|0.81971147|  PASSED
          sts_serial|   3|    100000|     100|0.64385034|  PASSED
          sts_serial|   4|    100000|     100|0.67349678|  PASSED
          sts_serial|   4|    100000|     100|0.15416763|  PASSED
          sts_serial|   5|    100000|     100|0.29761421|  PASSED
          sts_serial|   5|    100000|     100|0.30853436|  PASSED
          sts_serial|   6|    100000|     100|0.86217909|  PASSED
          sts_serial|   6|    100000|     100|0.61189123|  PASSED
          sts_serial|   7|    100000|     100|0.87697591|  PASSED
          sts_serial|   7|    100000|     100|0.95921884|  PASSED
          sts_serial|   8|    100000|     100|0.74492602|  PASSED
          sts_serial|   8|    100000|     100|0.88912784|  PASSED
          sts_serial|   9|    100000|     100|0.02658420|  PASSED
          sts_serial|   9|    100000|     100|0.10222474|  PASSED
          sts_serial|  10|    100000|     100|0.03401087|  PASSED
          sts_serial|  10|    100000|     100|0.91166190|  PASSED
          sts_serial|  11|    100000|     100|0.40653520|  PASSED
          sts_serial|  11|    100000|     100|0.53778823|  PASSED
          sts_serial|  12|    100000|     100|0.80985546|  PASSED
          sts_serial|  12|    100000|     100|0.23123896|  PASSED
          sts_serial|  13|    100000|     100|0.72981879|  PASSED
          sts_serial|  13|    100000|     100|0.52025530|  PASSED
          sts_serial|  14|    100000|     100|0.24454391|  PASSED
          sts_serial|  14|    100000|     100|0.26851145|  PASSED
          sts_serial|  15|    100000|     100|0.13334970|  PASSED
          sts_serial|  15|    100000|     100|0.81308797|  PASSED
          sts_serial|  16|    100000|     100|0.17512814|  PASSED
          sts_serial|  16|    100000|     100|0.09018089|  PASSED
         rgb_bitdist|   1|    100000|     100|0.93677992|  PASSED
         rgb_bitdist|   2|    100000|     100|0.02340170|  PASSED
         rgb_bitdist|   3|    100000|     100|0.99776745|   WEAK
         rgb_bitdist|   4|    100000|     100|0.59992524|  PASSED
         rgb_bitdist|   5|    100000|     100|0.30955805|  PASSED
         rgb_bitdist|   6|    100000|     100|0.87027149|  PASSED
         rgb_bitdist|   7|    100000|     100|0.95197441|  PASSED
         rgb_bitdist|   8|    100000|     100|0.84269892|  PASSED
         rgb_bitdist|   9|    100000|     100|0.34748187|  PASSED
         rgb_bitdist|  10|    100000|     100|0.71681849|  PASSED
         rgb_bitdist|  11|    100000|     100|0.41229819|  PASSED
         rgb_bitdist|  12|    100000|     100|0.98273999|  PASSED
rgb_minimum_distance|   2|     10000|    1000|0.77009233|  PASSED
rgb_minimum_distance|   3|     10000|    1000|0.57524337|  PASSED
rgb_minimum_distance|   4|     10000|    1000|0.00454860|   WEAK
rgb_minimum_distance|   5|     10000|    1000|0.22026032|  PASSED
    rgb_permutations|   2|    100000|     100|0.23772247|  PASSED
    rgb_permutations|   3|    100000|     100|0.03823947|  PASSED
    rgb_permutations|   4|    100000|     100|0.48103920|  PASSED
    rgb_permutations|   5|    100000|     100|0.85886410|  PASSED
      rgb_lagged_sum|   0|   1000000|     100|0.18563975|  PASSED
      rgb_lagged_sum|   1|   1000000|     100|0.95643512|  PASSED
      rgb_lagged_sum|   2|   1000000|     100|0.40632617|  PASSED
      rgb_lagged_sum|   3|   1000000|     100|0.17637298|  PASSED
      rgb_lagged_sum|   4|   1000000|     100|0.45128146|  PASSED
      rgb_lagged_sum|   5|   1000000|     100|0.55541504|  PASSED
      rgb_lagged_sum|   6|   1000000|     100|0.97326058|  PASSED
      rgb_lagged_sum|   7|   1000000|     100|0.83256108|  PASSED
      rgb_lagged_sum|   8|   1000000|     100|0.61127606|  PASSED
      rgb_lagged_sum|   9|   1000000|     100|0.42985876|  PASSED
      rgb_lagged_sum|  10|   1000000|     100|0.41418251|  PASSED
      rgb_lagged_sum|  11|   1000000|     100|0.51146094|  PASSED
      rgb_lagged_sum|  12|   1000000|     100|0.56179407|  PASSED
      rgb_lagged_sum|  13|   1000000|     100|0.82937810|  PASSED
      rgb_lagged_sum|  14|   1000000|     100|0.81265552|  PASSED
      rgb_lagged_sum|  15|   1000000|     100|0.34896824|  PASSED
      rgb_lagged_sum|  16|   1000000|     100|0.15237025|  PASSED
      rgb_lagged_sum|  17|   1000000|     100|0.83392657|  PASSED
      rgb_lagged_sum|  18|   1000000|     100|0.86312049|  PASSED
      rgb_lagged_sum|  19|   1000000|     100|0.07742212|  PASSED
      rgb_lagged_sum|  20|   1000000|     100|0.37033758|  PASSED
      rgb_lagged_sum|  21|   1000000|     100|0.43216894|  PASSED
      rgb_lagged_sum|  22|   1000000|     100|0.97366291|  PASSED
      rgb_lagged_sum|  23|   1000000|     100|0.70379788|  PASSED
      rgb_lagged_sum|  24|   1000000|     100|0.10270978|  PASSED
      rgb_lagged_sum|  25|   1000000|     100|0.68722156|  PASSED
      rgb_lagged_sum|  26|   1000000|     100|0.16262113|  PASSED
      rgb_lagged_sum|  27|   1000000|     100|0.97792972|  PASSED
      rgb_lagged_sum|  28|   1000000|     100|0.48595679|  PASSED
      rgb_lagged_sum|  29|   1000000|     100|0.75885757|  PASSED
      rgb_lagged_sum|  30|   1000000|     100|0.47496469|  PASSED
      rgb_lagged_sum|  31|   1000000|     100|0.06875677|  PASSED
      rgb_lagged_sum|  32|   1000000|     100|0.98162956|  PASSED
     rgb_kstest_test|   0|     10000|    1000|0.96442806|  PASSED
     dab_bytedistrib|   0|  51200000|       1|0.66598818|  PASSED
             dab_dct| 256|     50000|       1|0.15014667|  PASSED
Preparing to run test 207.  ntuple = 0
        dab_filltree|  32|  15000000|       1|0.23148953|  PASSED
        dab_filltree|  32|  15000000|       1|0.66925583|  PASSED
Preparing to run test 208.  ntuple = 0
       dab_filltree2|   0|   5000000|       1|0.59595166|  PASSED
       dab_filltree2|   1|   5000000|       1|0.11677795|  PASSED
Preparing to run test 209.  ntuple = 0
        dab_monobit2|  12|  65000000|       1|0.98119502|  PASSED

Run 3
ent output:

Entropy = 8.000000 bits per byte.

Optimum compression would reduce the size
of this 3145728000 byte file by 0 percent.

Chi square distribution for 3145728000 samples is 253.98, and randomly
would exceed this value 50.62 percent of the times.

Arithmetic mean value of data bytes is 127.4995 (127.5 = random).
Monte Carlo value for Pi is 3.141448769 (error 0.00 percent).
Serial correlation coefficient is -0.000014 (totally uncorrelated = 0.0).

dieharder output:

#            dieharder version 3.31.1 Copyright 2003 Robert G. Brown          #
   rng_name    |           filename             |rands/second|
 file_input_raw|                         fg3.bin|  5.54e+06  |
        test_name   |ntup| tsamples |psamples|  p-value |Assessment
   diehard_birthdays|   0|       100|     100|0.40338040|  PASSED
      diehard_operm5|   0|   1000000|     100|0.59478259|  PASSED
  diehard_rank_32x32|   0|     40000|     100|0.52896696|  PASSED
    diehard_rank_6x8|   0|    100000|     100|0.95455510|  PASSED
   diehard_bitstream|   0|   2097152|     100|0.51696104|  PASSED
        diehard_opso|   0|   2097152|     100|0.22323374|  PASSED
        diehard_oqso|   0|   2097152|     100|0.36968906|  PASSED
         diehard_dna|   0|   2097152|     100|0.00185043|   WEAK
diehard_count_1s_str|   0|    256000|     100|0.57326890|  PASSED
diehard_count_1s_byt|   0|    256000|     100|0.83872988|  PASSED
 diehard_parking_lot|   0|     12000|     100|0.94923891|  PASSED
    diehard_2dsphere|   2|      8000|     100|0.13498766|  PASSED
    diehard_3dsphere|   3|      4000|     100|0.67515912|  PASSED
     diehard_squeeze|   0|    100000|     100|0.22840132|  PASSED
        diehard_sums|   0|       100|     100|0.00032457|   WEAK
        diehard_runs|   0|    100000|     100|0.49802756|  PASSED
        diehard_runs|   0|    100000|     100|0.98157325|  PASSED
       diehard_craps|   0|    200000|     100|0.93565100|  PASSED
       diehard_craps|   0|    200000|     100|0.57679185|  PASSED
 marsaglia_tsang_gcd|   0|  10000000|     100|0.06196134|  PASSED
 marsaglia_tsang_gcd|   0|  10000000|     100|0.45878969|  PASSED
         sts_monobit|   1|    100000|     100|0.91706123|  PASSED
            sts_runs|   2|    100000|     100|0.70689416|  PASSED
          sts_serial|   1|    100000|     100|0.72773454|  PASSED
          sts_serial|   2|    100000|     100|0.65480309|  PASSED
          sts_serial|   3|    100000|     100|0.08769917|  PASSED
          sts_serial|   3|    100000|     100|0.96537626|  PASSED
          sts_serial|   4|    100000|     100|0.29487935|  PASSED
          sts_serial|   4|    100000|     100|0.30240110|  PASSED
          sts_serial|   5|    100000|     100|0.29330679|  PASSED
          sts_serial|   5|    100000|     100|0.81922667|  PASSED
          sts_serial|   6|    100000|     100|0.95896353|  PASSED
          sts_serial|   6|    100000|     100|0.58963017|  PASSED
          sts_serial|   7|    100000|     100|0.18378174|  PASSED
          sts_serial|   7|    100000|     100|0.01893783|  PASSED
          sts_serial|   8|    100000|     100|0.13901661|  PASSED
          sts_serial|   8|    100000|     100|0.82047418|  PASSED
          sts_serial|   9|    100000|     100|0.99736210|   WEAK
          sts_serial|   9|    100000|     100|0.33635566|  PASSED
          sts_serial|  10|    100000|     100|0.69851125|  PASSED
          sts_serial|  10|    100000|     100|0.78231771|  PASSED
          sts_serial|  11|    100000|     100|0.90879524|  PASSED
          sts_serial|  11|    100000|     100|0.95936497|  PASSED
          sts_serial|  12|    100000|     100|0.85017840|  PASSED
          sts_serial|  12|    100000|     100|0.93810643|  PASSED
          sts_serial|  13|    100000|     100|0.29099501|  PASSED
          sts_serial|  13|    100000|     100|0.26865484|  PASSED
          sts_serial|  14|    100000|     100|0.99875705|   WEAK
          sts_serial|  14|    100000|     100|0.85740032|  PASSED
          sts_serial|  15|    100000|     100|0.65366828|  PASSED
          sts_serial|  15|    100000|     100|0.97554415|  PASSED
          sts_serial|  16|    100000|     100|0.91608921|  PASSED
          sts_serial|  16|    100000|     100|0.95448406|  PASSED
         rgb_bitdist|   1|    100000|     100|0.21681436|  PASSED
         rgb_bitdist|   2|    100000|     100|0.05751244|  PASSED
         rgb_bitdist|   3|    100000|     100|0.98900249|  PASSED
         rgb_bitdist|   4|    100000|     100|0.89284281|  PASSED
         rgb_bitdist|   5|    100000|     100|0.83374660|  PASSED
         rgb_bitdist|   6|    100000|     100|0.47431641|  PASSED
         rgb_bitdist|   7|    100000|     100|0.53877719|  PASSED
         rgb_bitdist|   8|    100000|     100|0.82574326|  PASSED
         rgb_bitdist|   9|    100000|     100|0.42167025|  PASSED
         rgb_bitdist|  10|    100000|     100|0.90633840|  PASSED
         rgb_bitdist|  11|    100000|     100|0.71829837|  PASSED
         rgb_bitdist|  12|    100000|     100|0.58040873|  PASSED
rgb_minimum_distance|   2|     10000|    1000|0.96802310|  PASSED
rgb_minimum_distance|   3|     10000|    1000|0.18814919|  PASSED
rgb_minimum_distance|   4|     10000|    1000|0.02284249|  PASSED
rgb_minimum_distance|   5|     10000|    1000|0.09046293|  PASSED
    rgb_permutations|   2|    100000|     100|0.93885971|  PASSED
    rgb_permutations|   3|    100000|     100|0.66772808|  PASSED
    rgb_permutations|   4|    100000|     100|0.96049065|  PASSED
    rgb_permutations|   5|    100000|     100|0.99975661|   WEAK
      rgb_lagged_sum|   0|   1000000|     100|0.67142100|  PASSED
      rgb_lagged_sum|   1|   1000000|     100|0.44233671|  PASSED
      rgb_lagged_sum|   2|   1000000|     100|0.73193615|  PASSED
      rgb_lagged_sum|   3|   1000000|     100|0.37549273|  PASSED
      rgb_lagged_sum|   4|   1000000|     100|0.92244385|  PASSED
      rgb_lagged_sum|   5|   1000000|     100|0.92568253|  PASSED
      rgb_lagged_sum|   6|   1000000|     100|0.57496079|  PASSED
      rgb_lagged_sum|   7|   1000000|     100|0.88886376|  PASSED
      rgb_lagged_sum|   8|   1000000|     100|0.58412896|  PASSED
      rgb_lagged_sum|   9|   1000000|     100|0.43987345|  PASSED
      rgb_lagged_sum|  10|   1000000|     100|0.29758579|  PASSED
      rgb_lagged_sum|  11|   1000000|     100|0.26989399|  PASSED
      rgb_lagged_sum|  12|   1000000|     100|0.45817852|  PASSED
      rgb_lagged_sum|  13|   1000000|     100|0.69616494|  PASSED
      rgb_lagged_sum|  14|   1000000|     100|0.37199183|  PASSED
      rgb_lagged_sum|  15|   1000000|     100|0.01067473|  PASSED
      rgb_lagged_sum|  16|   1000000|     100|0.18369082|  PASSED
      rgb_lagged_sum|  17|   1000000|     100|0.58534250|  PASSED
      rgb_lagged_sum|  18|   1000000|     100|0.23158388|  PASSED
      rgb_lagged_sum|  19|   1000000|     100|0.04368539|  PASSED
      rgb_lagged_sum|  20|   1000000|     100|0.82555748|  PASSED
      rgb_lagged_sum|  21|   1000000|     100|0.60010186|  PASSED
      rgb_lagged_sum|  22|   1000000|     100|0.73140849|  PASSED
      rgb_lagged_sum|  23|   1000000|     100|0.00840861|  PASSED
      rgb_lagged_sum|  24|   1000000|     100|0.01872526|  PASSED
      rgb_lagged_sum|  25|   1000000|     100|0.11412705|  PASSED
      rgb_lagged_sum|  26|   1000000|     100|0.69801935|  PASSED
      rgb_lagged_sum|  27|   1000000|     100|0.07491189|  PASSED
      rgb_lagged_sum|  28|   1000000|     100|0.99062910|  PASSED
      rgb_lagged_sum|  29|   1000000|     100|0.10470245|  PASSED
      rgb_lagged_sum|  30|   1000000|     100|0.33499716|  PASSED
      rgb_lagged_sum|  31|   1000000|     100|0.15717211|  PASSED
      rgb_lagged_sum|  32|   1000000|     100|0.81830986|  PASSED
     rgb_kstest_test|   0|     10000|    1000|0.79008985|  PASSED
     dab_bytedistrib|   0|  51200000|       1|0.40621984|  PASSED
             dab_dct| 256|     50000|       1|0.36910998|  PASSED
Preparing to run test 207.  ntuple = 0
        dab_filltree|  32|  15000000|       1|0.62255692|  PASSED
        dab_filltree|  32|  15000000|       1|0.89873950|  PASSED
Preparing to run test 208.  ntuple = 0
       dab_filltree2|   0|   5000000|       1|0.11574121|  PASSED
       dab_filltree2|   1|   5000000|       1|0.45622515|  PASSED
Preparing to run test 209.  ntuple = 0
        dab_monobit2|  12|  65000000|       1|0.95595376|  PASSED

The above are the very first tests of FG that I got around to publish, despite having such hardware for more than half a year now. Others have done of course better than me and published their own tests waaaaay faster: mod6, danielpbarron, trinque, BingoBoingo. How about you, what's your own FG saying to you?

  1. Hey, they have been friendly with me, I don't know about you! Are you inca? 

May 24, 2018

A Tiny Stab at a Little Pricing Problem

Filed under: Eulora — DianaComan @ 10:57 p.m.

To start off, here's Foxy making disgusting goop in large quantities1:

Why is she making that? Well, for profit, what else. With each click, she's transforming 2852 ECu worth of rock-and-what-not into 4324 ECu worth of Disgusting Goop. That might not sound like much, except for the fact that it is effectively a 50% added value just like that in a few minutes (and while I sleep, yes, how else).

The above concrete numbers give me added ECu but also a way of approaching the ever-thorny euloran issue of pricing stuff. Only yesterday it would seem I failed at pricing some WPL correctly since the market (that had ASKED for WPL specifically) decided that... it was too expensive to bother buying it! So no sale made and a fee to pay instead2 but also a very clear and concrete thing to point to next time when anyone asks for WPL or complains that they don't have it.

Regardless of the market being there apparently completely lost in terms of what is how much and why would WPL cost more than dirt-cheap, lowest quality basic stuff, it's still worth to look again at some fresh data and see what prices make sense at all. Taking the Disgusting Goop above, let's calculate precisely what went in and what came out:

input: bundle of quality 595 + blueprint of quality 120 = 5.95*470 + 1.2*47 = 2852 ECu (quality adjusted base value3 )

output: 8 DG of quality 115 = 8*1.15*470 = 4324 ECu (quality adjusted base value)

Output / input = 4324/2852 = 1.51 (i.e. 151% or 51% gain).

Considering that the DG bundle is made only from harvestables4 it follows that Foxy simply can NOT sell those harvestables (rf, cr and sm) at anything less than 150% because at anything less than that she'd be better off using them as input to craft!  Notice also that the basic resources there (rf+cr) make only 2 thirds of the bundle, with sm the other third. For this little exercise I ignored the distinction between basic and non-basic harvestable but mining experience screams loud and clear that non-basic resources ARE harder to get in same quantities and same qualities. Which is not at all surprising given that they have higher value, doh.

As usual, in practice things are indeed a bit murkier, as all sorts of considerations quickly come stomping in: this 50% increase might be obtainable only at this specific sweet spot or only for this specific combination etc. Nevertheless, it IS some concrete data point in a sea of unknowns, so I'll stick to it for now. I'll add also that Foxy is a very skilled crafter (possibly even the top crafter at the moment) and it is for this reason that she *has this option* to make a significant profit just by crafting. Other players might find that the highest profit they can make out of harvestables really is by selling them at less than 150%, why not?

As Foxy's rather busy earning about 1500 ECu every couple of minutes for now, let's leave her aside for a moment and ask simply: what are *you* earning every couple of minutes and what are *your* options really?

  1. Yes, the red messages are all there one on top of the other because the bot is firing requests at the server without pause for clicking, eating, thinking or any of the other human-vices. 

  2. There is a fee for auctions without sale to discourage spam of useless auctions. 

  3. Also known as qabv and in any case the de facto *minimum* value of something in Eulora since that's what you can always get if you sell the item to the merchant NPC (i.e. to S.MG directly). 

  4. harvestables are obtained directly from euloran soil as a result of "mining" activity aka /explore + build; by contrast, craftables are items crafted as above, possibly from harvestables or other craftables 

May 3, 2018

EuCrypt Chapter 13: SMG RNG

Filed under: EuCrypt — DianaComan @ 3:01 p.m.

Motto: It's just the int interpretation of a float's binary representation.

~ This is part of the EuCrypt series. Start with Introducing EuCrypt. ~

This unexpected chapter equips EuCrypt with more convenient ways of using the excellent Fuckgoats (FG) for generating random numbers in various formats. The backstory is a heartwarming (if short) tale of idiocy stabbing itself in its own useless foot, so let's indulge for a moment.

As you might be aware, cryptography algorithms such as RSA and games such as Eulora rely to a significant extent on randomly generated numbers. As you might not fully appreciate though, the usual "random number generator" available on your computer is at best pseudo-random but the pseudo - here starts the idiocy - is not mentioned much, preferably not at all. So one gets /dev/random, /dev/urandom but never, ever, ever /dev/pseudorandom. One might say "what's in a name"1 and attempt to sort-of still work with it - let's just feed /dev/random with truly random bits from the FG and keep it around the house, as it might still be useful, why not? But of course the whole thing is made so that there isn't in fact a clear and straightforward way to even feed it better inputs - in other words, through its own working, /dev/random managed to push itself into being discarded even sooner rather than later. Isn't that... nice?

Once the silly idea of still using /dev/random in some way was thus abandoned as it should be, the only remaining thing was to provide some reliable ways of directly converting the raw random bits that FGs produce into some actual numbers of the sort that a user (a human, a game or anything else) needs in practice. Obviously, there can never be a full list of what sort of formats and ranges of numbers one might want, so this is by no means a comprehensive set or the only set of formats, ranges and even ways of converting FG bits into random numbers. It's simply a starter set of methods that are useful to S.MG at this time and may be perhaps useful to you at some time. As always, before using them, first read and understand their working and their limitations so that you can actually decide whether they meet your needs or not. And if they don't, either change them into what you need them to be or - even better yet - add to them your own methods that do exactly what you need them to do.

A random number generator based on FG would logically be a library on its own so that it can be easily used by any code - even without importing the whole EuCrypt if it doesn't need the rest. However, at the moment, the new code is simply an addition to truerandom.c that is part of smg_rsa, as it effectively builds on the other methods in there (those for accessing FGs specifically). I refrained from extracting the RNG into a separate module at this time because of a lack of tools: current vdiff does not know about simply moving code without changing it. As soon as the new vtools are ready and fully functional, it should be an easy task to simply move the relevant code to a different module with a short and easy to read vpatch (as opposed to the large delete & add vpatch that would result now from such a simple move). Until then at least, smg_rng will effectively be part of smg_rsa.

There are 4 new methods for obtaining random numbers using bits from a source of entropy2, providing the following types and ranges of numbers:

  • an unsigned integer between 0 and 2^32 - 1 (i.e. on precisely 32 bits): this method reads 32 bits from the specified entropy source and then copies them directly to the memory address of an uint32_t (unsigned integer on 32 bits) variable that is the result. Although working at bit-level, the method doesn't really care about endianness, since the bits are random anyway: sure, same bits will be interpreted as a different value by your Big Endian iron compared to your Little Endian iron but that doesn't make the series obtained with successive calls to this method from *the same machine* any less random.
  • an unsigned integer between 0 and 2^64 - 1 (i.e. on precisely 64 bits): this method is just like the above, but for larger numbers (64 bits instead of 32); specifically, this method reads 64 bits from the specified entropy source and then copies them directly to the memory address of an uint64_t (unsigned integer on 64 bits) variable that is the result. Although working at bit-level, the method doesn't really care about endianness, since the bits are random anyway: sure, same bits will be interpreted as a different value by your Big Endian iron compared to your Little Endian iron but that doesn't make the series obtained with successive calls to this method from *the same machine* any less random.
  • a "dirty" float between 0 and 1: this method obtains first a 32-bit random integer value with the relevant method above and then divides this (as a float) by the maximum possible value on 32 bits (2^32 - 1). The resulting float is deemed "dirty" from a randomness perspective because of the way in which floating points are stored: basically there will be some unpredictable rounding of the least significant bits so use this *only* if this degradation is insignificant to you.
  • a float between 1 and 2, assuming the IEEE 754/1985 internal representation: unlike the "dirty" float method, this one directly writes the random bits obtained from FG to the mantissa part of a float number in memory (it also sets the sign bit to 0 and the exponent to 127 effectively ensuring that the result is read as a positive float with value 1.mantissa). For clarity reasons, the code of this method actually writes first 32 random bits at the address of the desired float and then simply goes in and sets the sign to 0 and the exponent to 127, leaving the rest (i.e. the mantissa) with the random bits. Because of this direct bit-diddling, this method has to take into account the endianness: on Big Endian, the sign and exponent are the first two octets at the address of the float, while on Little Endian the exponent and sign are the last 2 octets. To handle this, the method first calls a little bit of new code that tests the endianness and then it sets accordingly the relevant offsets for the 2 octets that need diddling.

The signatures of the above methods as well as the new snippet of code for testing endianness at run-time are added to the relevant header file, eucrypt/smg_rsa/include/smg_rsa.h, together with the usual comments to help the reader understand the code.

The run-time test of endianness:

/* A way to determine endianness at runtime.
 * Required for diddling a float's mantissa for instance.
static const int onect = 1;
#define is_bigendian() ( (*(char*)&onect) == 0 )

The signatures of rng methods:

/* Returns (in parameter *n) a *potentially biased* random float between 0 and 1
 * Uses bits from ENTROPY_SOURCE but it rounds when converting to float
 * NB: This function rounds impredictably.
       Use it ONLY if LSB normalization is insignificant to you!
 * This function uses rng_uint64 below.
 * @param n - a float value (LSB rounded) between 0 and 1, obtained using
 *            a 64-bit random integer (64 bits from ENTROPY_SOURCE)
 * @return  - a positive value on success and a negative value in case of error
 *            main possible cause for error: failure to open ENTROPY_SOURCE.
 *            NB: a non-responsive/malconfigured source can result in blocking
int rng_dirty_float(float *n);

/* Returns (in parameter *n)  a randomly generated float between 1 and 2 using:
 *    - the IEEE 754/1985 format for single float representation
 *    - ENTROPY_SOURCE to obtain bits that are *directly* used as mantissa
 * NB: this value is between 1 and 2 due to the normalised format that includes
 *     an implicit 1 ( i.e. value is (-1)^sign * 2^(e-127) * (1.mantissa) )
 * From IEEE 754/1985, a description of the single float format:
 *   msb means most significant bit
 *   lsb means least significant bit
 *  1    8               23            ... widths
 * +-+-------+-----------------------+
 * |s|   e   |            f          |
 * +-+-------+-----------------------+
 *    msb lsb msb                 lsb  ... order

 * A 32-bit single format number X is divided as shown in the figure above. The
 * value v of X is inferred from its constituent fields thus:
 * 1. If e = 255 and f != 0 , then v is NaN regardless of s
 * 2. If e = 255 and f = 0 , then v = (-1)^s INFINITY
 * 3. If 0 < e < 255 , then v = (-1)^s * 2^(e-127) * ( 1.f )
 * 4. If e = 0 and f != 0 , then v = (-1)^s * 2^(-126) * ( 0.f ) (denormalized
 *    numbers)
 * 5. If e = 0 and f = 0 , then v = ( -1 )^s * 0 (zero)
 * @param n - the address of an IEEE 754/1985 float: its mantissa will be set to
 *              random bits obtained from ENTROPY_SOURCE; its sign will be set
 *              to 0; its exponent will be set to 127 (the bias value so
 *              that the actual exponent is 0).
 * @return  - a positive value on success and a negative value in case of error
 *              main possible cause for error: failure to open ENTROPY_SOURCE.
 *              NB: a non-responsive/malconfigured source can result in blocking
int rng_float_754_1985(float *n);

/* Returns (in parameter *n) a random unsigned integer value on 32 bits.
 * Uses random bits from ENTROPY_SOURCE that are directly interpreted as int
 * @param n - it will contain the random integer obtained by interpreting 32
 *            bits from ENTROPY_SOURCE as an unsigned int value on 32 bits.
 * @return  - a positive value on success and a negative value in case of error
int rng_uint32( uint32_t *n );

/* Returns (in parameter *n) a random unsigned integer value on 64 bits.
 * Uses random bits from ENTROPY_SOURCE that are directly interpreted as int
 * @param n - it will contain the random integer obtained by interpreting 64
 *            bits from ENTROPY_SOURCE as an unsigned int value on 64 bits.
 * @return  - a positive value on success and a negative value in case of error
int rng_uint64( uint64_t *n );

The actual implementation of the above methods is in eucrypt/smg_rsa/truerandom.c:

int rng_dirty_float(float *n) {
  int status;   /* for aborting in case of error */
  uint32_t r;   /* a random value on 32 bits */
  uint32_t maxval = 0xffffffff; /* maximum value on 32 bits */

  /* obtain a random number on 32 bits using ENTROPY_SOURCE */
  status = rng_uint32( &r );
  if ( status < 0 )
    return status;

  /* calculate and assign the floating-point random value as (r*1.0)/max val */
  /* multiplication by 1.0 IS NEEDED to do float division rather than int div*/
  *n = ( r * 1.0 ) / maxval;

  return 1;

int rng_float_754_1985(float *n) {
  /* Single float ieee 754/1985 has 23 bits that can be set for the mantissa
   * (and one implicit bit=1).
   * Full single float ieee 754/1985 representation takes 4 octets in total.
  int noctets = 4; /* number of octets to read from ENTROPY_SOURCE */
  int nread;       /* number of octets *read* from ENTROPY_SOURCE  */
  unsigned char bits[ noctets ]; /* the random bits from ENTROPY_SOURCE */
  int oSignExp, oExpM;/* offsets for sign+exponent octet, exponent+mantissa*/

  /* obtain random bits */
  nread = get_random_octets( noctets, bits );

  if (nread != noctets )
    return -1;  /* something wrong at reading from ENTROPY_SOURCE, abort */

  /* set offsets for bit diddling depending on endianness of iron */
  if (is_bigendian()) {
    oSignExp = 0;
    oExpM = 1;
  else {
    oSignExp = 3;
    oExpM = 2;

  /* set sign=0; exponent=127; explicit mantissa = random bits (23 bits) */
  *(bits+oExpM) = *(bits+2) | 0x80;  /* one bit of exponent set */
  *(bits+oSignExp) = 0x3f;           /* sign=0; exponent bits for 127 */

  /* now copy the bits to the result var (i.e. as a float's representation */
  memcpy( n, bits, noctets );
  return 1;

int rng_uint32( uint32_t *n ) {
  int noctets = 4;  /*  32 bits aka 4 octets to read from ENTROPY_SOURCE     */
  int nread;        /*  the number of octets read from ENTROPY_SOURCE        */
  unsigned char bits[ noctets ]; /* for storing the bits from ENTROPY_SOURCE */

  /* read random 32 bits from ENTROPY_SOURCE */
  nread = get_random_octets( noctets, bits );
  if ( nread != noctets )
    return -1;

  /* copy the random bits to n, to be interpreted as uint32 */
  /* endianness is irrelevant here - the bits are random anyway */
  memcpy( n, bits, noctets );

  return 1;

int rng_uint64( uint64_t *n ) {
  int noctets = 8;  /*  64 bits aka 8 octets to read from ENTROPY_SOURCE     */
  int nread;        /*  the number of octets read from ENTROPY_SOURCE        */
  unsigned char bits[ noctets ]; /* for storing the bits from ENTROPY_SOURCE */

  /* read random 64 bits from ENTROPY_SOURCE */
  nread = get_random_octets( noctets, bits );
  if ( nread != noctets )
    return -1;

  /* copy the random bits to n, to be interpreted as uint64 */
  /* endianness is irrelevant here - the bits are random anyway */
  memcpy( n, bits, noctets );

  return 1;

As usual, for every new piece of code, there are also new tests. In this case, the tests are very basic, simply calling each method and reporting both the resulting number and the status code (i.e. whether the method reported any errors). Note that assessing the outputs of a random number generator is way beyond the scope of those basic tests - you should devise and use your own tools for evaluating (to a degree that is satisfying for yourself) the resulting sequence of numbers obtained through repeated calls to any or all of these methods. The new tests in eucrypt/smg_rsa/tests/tests.c:

void test_dirty_float_rng( int nruns ) {
  int i, status;
  float dirty;

  printf("Running test for smg rng dirty float with %d runsn", nruns);
  for (i=0; i0 ? "OK" : "FAIL");

void test_ieee_float_rng( int nruns ) {
  int i, status;
  float ieee;

  printf("Running test for smg rng ieee 745/1985 float with %d runsn", nruns);
  for (i=0; i0 ? "OK" : "FAIL");

void test_uint32_rng( int nruns ) {
  int i, status;
  uint32_t n;

  printf("Running test for smg rng unsigned int32 with %d runsn", nruns);
  for (i=0; i0 ? "OK" : "FAIL");

void test_uint64_rng( int nruns ) {
  int i, status;
  uint64_t n;

  printf("Running test for smg rng unsigned int64 with %d runsn", nruns);
  for (i=0; i0 ? "OK" : "FAIL");

The .vpatch for the above smg rng implementation can be found on my Reference Code Shelf as well as below:

  1. A full backstory, at the very least! But let's not digress even more from the code... 

  2. The source of entropy is assumed to be a FG but - unlike /dev/urandom - you can change this quite easily. 

Older Posts »

Theme and content by Diana Coman