【技术】内部数值存储研究
fx-es(ms)吧
全部回复
仅看楼主
level 12
masmyc 楼主
字符表
镇楼

帖子会在接下来的几天内慢慢继续更新,请各位别着急。
2014年01月02日 11点01分 1
level 13
一个有姿势的二楼
2014年01月02日 11点01分 2
level 12
masmyc 楼主
@骆奕扬 曾经说过楼主善于利用M值。并且发明了魔数法来辅助拼字。下面来谈谈这样的数是怎么构造出来的。
楼楼的技术比不上本吧各位大神。吧内也有其他谈内部数值存储的帖子。但是我希望我这篇帖子更清晰。
2014年01月02日 11点01分 3
魔数法参见《【991+】【新手向】一步步教你打 I love you》贴。
2014年01月02日 12点01分
level 13

2014年01月02日 11点01分 4
level 12
masmyc 楼主
此帖子以 fx-991ES PLUS 为参考型号。因为楼楼用的就是这个型号。
一、有哪些数值存储方式
根据目前的研究,991+一共有浮点、分数、根式、复数、指针、特殊值这五种存储方式。
浮点:±a×10^n 其中 0≤a<10 -99≤n≤99。
分数:±a/b 其中a和b以十进制表示的位数之和不超过9。
根式:±(a√(b)+c√(d))/e 目前楼主对于 a b c d e 的取值范围不太了解。但是 a b c d e 都可以取 0 或者 1。
复数:±a×10^n±b×10^m
i 其中 0≤(a,b)<10 -99≤(n,m)≤99。
指针:目前已知 MatA/VctA (0x60) MatB/VctB (0x61) MatC (0x62) MatAns/VctAns (0x63)。
特殊值:目前已知 ERROR (0xF3)。
2014年01月02日 11点01分 5
参考佳能说明书
2014年01月15日 12点01分
根式的
2014年01月15日 12点01分
level 10

[Yeah]
2014年01月02日 11点01分 6
level 11

2014年01月02日 11点01分 7
level 12
masmyc 楼主

二、变量存在哪?
目前发现变量 M Ans A B C D E F X Y 是依次存储的,每一个变量占用10字节。
M 的存储位置是基本溢出缓冲区便宜量 +0xCA。也就是紧挨着随机数种子(即不稳定字符,占2字节)存储的。
变量的很多存储方式是用 BCD 码来存储。也就是说这一系列计算器的计算实际上是用十进制的,而不是二进制。这也是为什么这一系列计算器在做大量运算的时候比较慢,但是却不会产生类似计算机 IEEE 浮点数在做二进制运算的时候产生的误差。
复数的实部存储在我所说的地方,而虚部存储在另外的地方,也是各占用10字节(这可以从 CMPLX 溢出模式的种种异常现象研究出来,参考楼主的《【991+】A^0法溢出r!比M^0法节省57%按键次数!》)。这片存储区域在退出 CMPLX 的时候可能会被别的模式的存储区域复写。
矩阵和向量的内容也是存储在另外的地方的,并且那地方和 COMP 模式的历史记录缓冲区貌似共用内存(在 COMP 模式爆出矩阵后输入很长的算式按等号会导致矩阵内容爆出 ERROR,参考楼主的《【991+】不进乱点模式爆矩阵!》)。这片存储区域在退出 MATRIX 的时候会把 MatA/VctA MatB/VctB MatC 清零,但是 MatAns/VctAns 不清,在进入别的模式的时候可能会被覆盖。
2014年01月02日 11点01分 8
订正错别字 便宜→偏移。
2014年01月02日 12点01分
MatAns不清?那覆盖的时候会不会只覆盖一半,下次进入产生异常?
2014年01月02日 14点01分
VCT也有VCTC的[挠墙]
2014年01月07日 04点01分
回复 1095831543 :写这篇文章的时候楼主把991丢在家了……记岔了不好意思。
2014年01月07日 04点01分
level 13

2014年01月02日 12点01分 9
level 12
masmyc 楼主

(顺便提一下)为什么计算器要分模式?
计算器分模式可不是为了在卖的时候能够体现出自己功能多,而是为了节省内存,同时可以实现开关不同的模式来实现同一个固件在不同型号计算器下有不同的功能(这也是为什么会有软升级)。
其实,如果不分模式,COMP CMPLX BASE-N 等模式是可以挤在一起的。MATRIX VECTOR 也是可以的。STAT TABLE 就更不用说了。但是众所周知,计算器的内存很有限。这么多功能,全部载入 RAM 中是不可能的。于是就采用了当年 MS-DOS 应用程序采用的一个技术——Overlay。也就是不同的模式共用一块内存。载入新模式的时候覆盖旧的内存。
分模式也有利于降低开发难度,减少 bug。多种型号的硬件共用同一个固件并打开不同的模式也可以降低开发成本(程序员的工资比流水线工人的工资高啊)。
如何利用这种功能?
我们在某些特定的溢出状态下,需要了解哪些内容共用一块内存来构造合适的数值进行下一步操作。类似于攻击计算机操作系统,需要对内存布局和内核架构有一定了解,研究计算器的异常也需要对内存有一定了解。对于 82ES 等型号,官方公布了模拟器,可以用模拟器配合 WinHex 来研究;而对于 991ES PLUS 等型号,只有摸黑试了,楼主在 1L 的字符表正是用刷不稳定字符的方法得到的。
2014年01月02日 12点01分 10
level 12
masmyc 楼主

三、白值是怎么回事?
白值不仅仅是一种情况。只要是无法显示的数值都可能变成白值/ERROR/死机。当然 ERROR 也可以是计算器预料之中的 0xF3 特殊值。
比如 5L 说到浮点 ±a×10^n 的取值范围是 0≤a<10 -99≤n≤99。如果 a 不满足这个取值范围,则会导致白值。如果 n 不满足,可能会被截头或溢出或死机。
2014年01月02日 12点01分 11
level 12
masmyc 楼主
下面一帖说浮点的存储。楼楼先慢慢码字,你们随便插楼,今天如果码好了就今天发,如果今天没有码好就明天发。
2014年01月02日 12点01分 12
level 13

2014年01月02日 12点01分 13
level 12
ls插了四次了
2014年01月02日 12点01分 14
正常现象,插十几次的也不是没有
2014年01月02日 14点01分
level 10
技术贴[大拇指]
2014年01月02日 14点01分 15
level 11
后排留名
2014年01月02日 15点01分 16
level 13
居然精了?!
2014年01月02日 15点01分 17
虽然我不是首发(前人的经验+自己的创新),而且关键的部分我还没有写到,但是大概是吧主希望我能继续写下去,才给了我精吧。
2014年01月02日 16点01分
@masmyc 又不精了
2014年01月03日 00点01分
level 12
masmyc 楼主
自然语言的解释还没有码好,预计明天发。
在《求问关于M的事情》一贴中 @lhy7715 提到可否用 C 语言来描述一下,下面放代码:
struct storage_area {
unsigned long long int padding; /* off+0xC0 */
unsigned /* little_endian */ short int rand_seed; /* off+0xC8 */
struct value_var M, Ans, A, B, C, D, E, F, X, Y; /* off+0xCA */
};
struct value_var {
unsigned char data[8]; /* BCD code, magnitude */
unsigned char exp; /* BCD code, two's complement */
unsigned char sign;
}
#define odd(x) ((x) & 0x1)
#define bcd2int(bcd) ((((bcd) >> 4) & 0xf)*10+((bcd) & 0xf))
#define get_value_var_type(x) ((x).data[0] >> 4)
#define get_value_var_digit(x, digit_no) ((x).data[(digit_no)/2] >> (odd((digit_no)) ? 0 : 4) & 0xF) /* 1 <= digit_no <= 15 */
/* Values for value_var.sign */
#define VALUE_VAR_SIGN_POS_NEG 0x0 /* 0 <= x < 1 */
#define VALUE_VAR_SIGN_POS_POS 0x1 /* x > 1 */
#define VALUE_VAR_SIGN_NEG_NEG 0x5 /* -1 < x < 0 */
#define VALUE_VAR_SIGN_NEG_POS 0x6 /* x <= -1 */
看不懂的等我的自然语言详解。
2014年01月02日 16点01分 18
level 12
masmyc 楼主
五、浮点格式
十个字节,如下定义:
字节1,高4位:变量类型域,应为 0x0。
字节1,低4位:第一位十进制有效数字。
字节2,高4位:第二位十进制有效数字。
字节2,低4位:第三位十进制有效数字。
……
字节8,低4位:第十五位十进制有效数字。
字节9:指数,用BCD解码,负数用反码,稍后解释。
字节10:符号位:
0x00:0≤X<1
0x01:X≥1
0x05:-1<X<0
0x06:X≤-1
2014年01月03日 12点01分 21
level 12
masmyc 楼主
下面我来举例子:
令 M=5.42694682881413×10^81
内存为 05 42 69 46 82 88 14 13 81 01
令 M=4.55070183730897×10^-32
内存为 04 55 07 01 83 73 08 97 68 00 (注意 68=100-32,正所谓反码表示负数)
令 M=-7.65120911691×10^57
内存为 07 65 12 09 11 69 10 00 57 06 (注意末位补零)
令 M=-7.46426841128546×10^-18
内存为 07 46 42 68 41 12 85 46 82 05
2014年01月03日 17点01分 23
1 2 3 尾页