gemot encubed  

Go Back   gemot encubed > Gemot > Production & Help > White Album 2 Bytecode

Production & Help For discussions regarding production aspects, especially localisation, of visual novels and related games.

Thread: White Album 2 Bytecode Reply to Thread
Your Username: Click here to log in
Random Question
Post Icons
You may choose an icon for your message from the following list:

Additional Options
Miscellaneous Options

Topic Review (Newest First)
2012-03-06 14:19
jonathanasdf Ok, we are now done deciphering the .bnr format. The only problems now are some unrecognized game flag ids (we have figured out that they are set when a song is unlocked for bgm mode), and that there are lots of functions that we don't know what they do, but these problems are not important for translation. Now we can start writing a tool to import/export .bnrs and start translation!
2012-02-28 12:48
jonathanasdf Some more updates:

The unknown value before the header seems to be the address of the first thing after the header. Seems redundant though if header size is there too :\

You CAN jump into the middle of a .bnr file using LoadScript/CallScript referencing the header of the file you're calling

0x06 0x00 is assign (x = y)

0x02 0xaa seems to be push arr_aa where arr_aa is a local array.

0x06 0x1B seems to be array dereferencing.
0x02 0x01 0x05 0x03 0x00 0x06 0x1B seems to give you the variable arr_01[0].
2012-02-25 17:20
0x01 and 0x02 should be for int8 and int16 as I said before.
Is that not for the argument to 0x05, which means push constant? eg 0x05 0x01 xx means push int8? I'm talking about the opcodes 0x01 and 0x02.

So far what we know is that
0x00 is various statements
0x03 is push line from corresponding .txt file
0x04 is call function
0x05 is push constant
0x06 is perform various operations

just 0x01 and 0x02 are missing.
2012-02-24 16:48
Should probably note that the names of some of those variables are spoilers for anyone who hasn't played WA2 yet. ;)
2012-02-24 12:48
0x01 and 0x02 should be for int8 and int16 as I said before.

Not sure if you can define variables within .bnr files, but there are some global ones in GFLAG.dat and Global.vrb:


2012-02-24 11:05
jonathanasdf Still, I wonder how do you create or use a variable? Also, what do the opcodes 0x01 and 0x02 do...
2012-02-22 19:50
jonathanasdf My theory is that type6 means anything, because print can take a float as well.
Your idea about line skipping is interesting, maybe 0x84 has to do with that?
2012-02-22 19:20
Originally Posted by jonathanasdf View Post
Actually, 0x83 is SetMessageE and 0x84 is EndMessage, and 0x84 does take 1 parameter.
Oh, right. Looks like I mixed them up.

Originally Posted by jonathanasdf View Post
Nice! too bad that doesn't tell us what the parameters do :(
Haha, that would be great, wouldn't it. What we have here though, is more than one could hope for. I wonder if the game still runs without the .fnc files... Nah, it doesn't. Tried it now, threw out a couple of errors and crashed.

Mapping function codes with their names was actually the last distinct objective I had in mind, but now that I think about it, there are these parameter types. We already know about type3 (int32), type4 (float) and type5 (string index). For the remaining ones, here are all the examples:



I think type6 is either signed integer (assuming type3 is unsigned) as WN() can take -1 to clear the speaker tag, or an indicator that the value can be type3 or type5. Second one sounds more likely.

As for type7, we know that second parameter of SetMessageE() is some incremental number. One thing that comes to mind is it could be some kind of index, a variable index perhaps. It could be for keeping track of which lines are read and which of them or not, and to keep them in save files. We may be able to test this theory by changing some values and checking if it breaks line skipping.

As you can see, assuming that my interpretation was correct, some parameters have default values. The default value for SEP()'s volume parameter is 0xFF, for instance. But how are they used? I think either all the functions in .bnr files have their proper arguments, or there is some other opcode we're currently unaware of to push the default argument onto stack.
2012-02-22 17:42
jonathanasdf Nice! too bad that doesn't tell us what the parameters do :(
But at least the function names seem logical, so that should aid a lot in determining what the function does. For the tool though I'd like to stick to our names since for the most cases it's more informative.

My interpretations:

And I might as well list down the functions from the script files here then, for simplifying future lookup (this is copied from your previous post).

Actually, 0x83 is SetMessageE and 0x84 is EndMessage, and 0x84 does take 1 parameter.

2012-02-22 12:57
Well, at least one of the parameters is bound to be a variable. Otherwise there would be no point in adding two constant numbers; you would just pass the result directly to the function. Though it is still possible to do so I guess, using 0x06 0x10 instead of 0x06 0x01, for example.

I think I got the function mapping pattern by the way, which turned out to be quite simpler than I imagined. LFScriptFunc.fnc includes function codes between 0x00-0x12: Your "callBnr" is actually "SLoad", "callBnrAndReturn" is "SCall", "alert" is "print", and so on. As for LFScriptFuncEx.fnc, the first one is 0x80, so you just need to add 128 to a function's zero-based index to get its code. The ones you've confirmed so far through 0x83-0xC2 seem to fit this pattern at least:


This also explains your comment on 0x84:
This does not seem to be needed to show the text or the backlog, but 0x84 always follows 0x83. It takes 1 parameter, but changing it doesn't seem to affect anything.
0x84 (WaitMessage2) doesn't actually take any parameter, but it's there for whatever reason anyway.
2012-02-21 21:16
jonathanasdf So that's just a normal or.

I think that for 0x06 0x01 to 0x07 it's not what you have written there, but rather x = x+y, x = y-x, etc. At least, when I try with

05 03 05 05 03 07 06 01 04 04 06 1E

etc, it gives the error 変数以外に=式は使えません
Which also implies that there's the concept of variables.

for 0x06 0x08 onwards it's right.
2012-02-21 13:44
Oh, you're right, my mistake. Now that I take another look, it's actually like this:

if (x || y) {
  return 1;
} else {
  return x;
2012-02-21 12:17
jonathanasdf So that means...
0x0E: if (!(x || y)) return x
will ALWAYS return 0 :\

From 9999.bnr it seems 0x07 is switch, 0x08 is case, 0x09 is default, and 0x0A is break. From what you say there, I guess 0x00 is false and 0x01 is true.
Edit: hm, it seems that if it reaches a statement 0x00 0x00 then it crashes. Also, it seems that the stack defaults to giving a value of 0 if you try to access it and it's empty.

Yes we are planning to change the font eventually.

Sorry, haven't got a clue. They may very well be offset labels though.
That's the best theory I've heard so far. Makes sense, since I was trying to call bnr scripts and passing values to the 2nd parameter thinking it might've been an offset into the script, but all that did was crash the game.
2012-02-21 10:47
Originally Posted by jonathanasdf View Post
Hm, can you expand on this? In particular, do you have any idea what the items are used for?
Sorry, haven't got a clue. They may very well be offset labels though.

Originally Posted by jonathanasdf View Post
We were planning to use a full-width comma as a replacement for a comma+space (visually it looks quite fine) but this is probably better.
You may want to edit the font file (fnt.pak) for better-looking Latin characters. To Heart 2 is based on the same engine (probably an older version, haven't checked) and looks like its translation team did just that. Oh, wait. You probably already know that since you're working with velocity7.

Originally Posted by jonathanasdf