diff --git a/apps/pdp10/diags/ka10/dakal/README.md b/apps/pdp10/diags/ka10/dakal/README.md index 1aa4c5609..eabb159ed 100644 --- a/apps/pdp10/diags/ka10/dakal/README.md +++ b/apps/pdp10/diags/ka10/dakal/README.md @@ -7,7 +7,7 @@ machines: type: pdp10 config: /devices/pdp10/machine/ka10/test/debugger/machine.xml debugger: true - commands: a dakal.mac; g 31134 + commands: a dakal.mac; g 33726 --- PDP-10 KA10 Basic Instruction Diagnostic #12 @@ -192,6 +192,10 @@ Here's that output: MUL(252525252525,004000000000) PDP-10: 124000000000 JavaScript: 524000000000 @032765 MUL(252525252525,020000000000) PDP-10: 120000000000 JavaScript: 520000000000 @033013 MUL(252525252525,100000000000) PDP-10: 100000000000 JavaScript: 500000000000 @033041 + MUL(400000000000,400000000000) PDP-10: 400000000000 JavaScript: 000000000000 @033707 VERIFIED + MUL(400000000000,400000000000) PDP-10: 400000000000 JavaScript: 000000000000 @033707 VERIFIED + MUL(400000000000,400000000000) PDP-10: 400000000000 JavaScript: 000000000000 @033707 VERIFIED + MUL(400000000000,400000000000) PDP-10: 400000000000 JavaScript: 000000000000 @033707 VERIFIED MUL(777777777776,777777777776) PDP-10: 000000000004 JavaScript: 000000000000 @033726 MUL(000000777777,000000777777) PDP-10: 377776000001 JavaScript: 777776000001 @033726 MUL(000000777777,000000777777) PDP-10: 377776000001 JavaScript: 777776000001 @033726 diff --git a/modules/pdp10/lib/cpuops.js b/modules/pdp10/lib/cpuops.js index 011c702ab..187fe0d04 100644 --- a/modules/pdp10/lib/cpuops.js +++ b/modules/pdp10/lib/cpuops.js @@ -6531,12 +6531,21 @@ PDP10.split72 = function(res, ext, fExternal) var sign = ext - (ext % PDP10.INT_LIMIT); ext = ((ext * 2) % PDP10.WORD_LIMIT) + Math.trunc(res / PDP10.INT_LIMIT); res = sign + (res % PDP10.INT_LIMIT); - if (fExternal) return res; var signNew = ext - (ext % PDP10.INT_LIMIT); if (sign != signNew) { - ext = sign + (ext - signNew); - this.regPS |= PDP10.PSFLAG.AROV; + /* + * I used to restore ext's original sign (ext = sign + (ext - signNew)), but the PDP-10's defined + * behavior for multiplication overflow (ie, whenever both operands are 0o400000000000) is to set both + * res and ext to 0o400000000000. + * + * To quote the original spec for the MUL instruction: + * + * If both operands are -2^35 set Overflow; the double length result stored is -2^70. + */ + res = ext; + if (!fExternal) this.regPS |= PDP10.PSFLAG.AROV; } + if (fExternal) return res; this.regEX = res; return ext; }; diff --git a/versions/pdpjs/1.34.3/pdp10-dbg.js b/versions/pdpjs/1.34.3/pdp10-dbg.js index b2716f70a..582b41a1a 100644 --- a/versions/pdpjs/1.34.3/pdp10-dbg.js +++ b/versions/pdpjs/1.34.3/pdp10-dbg.js @@ -111,7 +111,7 @@ function ie(a,b){var c=this.f(this.b),d=c;if(a&=384)switch(d&=x,a){case 256:d+=x function oe(){}function pe(){}function L(a){this.u("undefined opcode: "+va(a));sd(this,-1);this.Y()}function qe(a){a>z&&(a!=B?a=Xb-a:this.j|=163840);return a}function Q(a,b){var c=(a+b)%D;re.call(this,a,b,c);return c} function se(a,b,c){var d=!1,e=!1,f=b-b%B;a=a%B+b*B%D;b=this.F=f+Math.trunc(b/2);c>z&&(c=D-c,d=!d);b>z&&(a?(b=C-b,a=D-a):b&&(b=D-b),e=!0,d=!d);if(b>=c)return this.j|=131104,-1;f=this.kb;f[0]=0;f[1]=0;f=this.wa;f[0]=1;f[1]=0;f=this.oa;f[0]=c;f[1]=0;c=this.xa;c[0]=a;for(c[1]=b;0b[0]&&(b[0]+=D,b[1]--),ue(this.kb,this.wa),ve(this.xa)))break;we(this.oa);we(this.wa)}while(!ve(this.wa)); a=this.kb[0];this.F=this.xa[0];d&&a&&(a=D-a);e&&this.F&&(this.F=D-this.F);return a} -function xe(a,b,c,d){var e=a,f=b;b=!1;var g;e>z&&(d||1001!=this.nb||e!=B)&&(e=D-e,b=!b);f>z&&(f=D-f,b=!b);if(ez)&&(g!=C||a<=z)&&(this.j|=131072),a;c=a;b=g;a=b-b%B;b=2*b%D+Math.trunc(c/B);c=a+c%B;d?d=c:(d=b-b%B,a!=d&&(b=a+(b-d),this.j|=131072),this.F=c,d=b);return d} +function xe(a,b,c,d){var e=a,f=b;b=!1;var g;e>z&&(d||1001!=this.nb||e!=B)&&(e=D-e,b=!b);f>z&&(f=D-f,b=!b);if(ez)&&(g!=C||a<=z)&&(this.j|=131072),a;c=a;b=g;a=b-b%B;b=2*b%D+Math.trunc(c/B);c=a+c%B;a!=b-b%B&&(c=b,d||(this.j|=131072));d?d=c:(this.F=c,d=b);return d} function ye(a){a?a==B?this.j|=163840:a=Xb-a:this.j|=98304;return a}function ze(a,b){var c=a-b;0>c&&(c+=D);re.call(this,c,b,a);return c}function re(a,b,c){a=Math.trunc(a/Wb);b=Math.trunc(b/Wb);c=Math.trunc(c/Wb);var d=a^(a^b)&(b^c);this.j=this.j|(d&2?65536:0)|(d&1?32768:0)|((a^c)&(b^c)&2?131072:0)}function R(a,b){return((a/E|0)&(b/E|0))*E+((a&b)>>>0)}function S(a,b){return R(a,(~(b/E|0)&15)*E+(~b>>>0))}function T(a,b){return(a>>0)}function U(a,b){return(a/E|0|b/E|0)*E+((a|b)>>>0)}function V(a){return a>>0)}function X(a){return(a/y|0)+(a&x)*y}function fe(a,b,c){switch(a&384){case 0:b-=b&x;break;case 128:b=0;break;case 256:b=x*y;break;case 384:b=c>Ub?x*y:0}return b}function Gd(a,b,c){switch(a&384){case 0:b&=x;break;case 128:b=0;break;case 256:b=x;break;case 384:b=c>z?x:0}return b} function ue(a,b){a[0]+=b[0];a[1]+=b[1];a[0]>=D&&(a[0]%=D,a[1]++)}function te(a,b){var c=a[1]-b[1];c||(c=a[0]-b[0]);return c}function we(a){a[1]%2&&(a[0]+=D);a[0]=Math.trunc(a[0]/2);a[1]=Math.trunc(a[1]/2)}function ve(a){return!a[0]&&!a[1]} diff --git a/versions/pdpjs/1.34.3/pdp10.js b/versions/pdpjs/1.34.3/pdp10.js index 0bc553329..99a4eec93 100644 --- a/versions/pdpjs/1.34.3/pdp10.js +++ b/versions/pdpjs/1.34.3/pdp10.js @@ -103,7 +103,7 @@ function Dc(a,b){var c=this.b(this.a)&C,d=this.b(b);this.c(b,Ec(a,d,c)+c)}functi function Kc(a,b){b=this.b(b)/E|0;var c=this.b(this.a);this.c(this.a,Ec(a,c,b)+b)}function Lc(a,b){var c=this.b(this.a),d=c/E|0,c=Ec(a,c,d)+d;this.c(this.a,c);b&&this.c(b,c)}function Q(a){Mc[a&7].call(this,a,a>>3&127)}function Nc(){}function Oc(){}function O(a){this.M("undefined opcode: "+ka(a));this.f=(this.f+-1)%$a;N(this)}function Pc(a){a>F&&(a!=G?a=db-a:this.g|=163840);return a}function R(a,b){var c=(a+b)%J;Qc.call(this,a,b,c);return c} function S(a,b,c){var d=!1,e=!1,f=b-b%G;a=a%G+b*G%J;b=this.o=f+Math.trunc(b/2);c>F&&(c=J-c,d=!d);b>F&&(a?(b=I-b,a=J-a):b&&(b=J-b),e=!0,d=!d);if(b>=c)return this.g|=131104,-1;f=this.Na;f[0]=0;f[1]=0;f=this.da;f[0]=1;f[1]=0;f=this.X;f[0]=c;f[1]=0;c=this.ea;c[0]=a;for(c[1]=b;0b[0]&&(b[0]+=J,b[1]--),Sc(this.Na,this.da),Tc(this.ea)))break;Uc(this.X);Uc(this.da)}while(!Tc(this.da)); a=this.Na[0];this.o=this.ea[0];d&&a&&(a=J-a);e&&this.o&&(this.o=J-this.o);return a} -function Vc(a,b,c,d){var e=a,f=b;b=!1;var g;e>F&&(d||1001!=this.Wa||e!=G)&&(e=J-e,b=!b);f>F&&(f=J-f,b=!b);if(eF)&&(g!=I||a<=F)&&(this.g|=131072),a;c=a;b=g;a=b-b%G;b=2*b%J+Math.trunc(c/G);c=a+c%G;d?d=c:(d=b-b%G,a!=d&&(b=a+(b-d),this.g|=131072),this.o=c,d=b);return d} +function Vc(a,b,c,d){var e=a,f=b;b=!1;var g;e>F&&(d||1001!=this.Wa||e!=G)&&(e=J-e,b=!b);f>F&&(f=J-f,b=!b);if(eF)&&(g!=I||a<=F)&&(this.g|=131072),a;c=a;b=g;a=b-b%G;b=2*b%J+Math.trunc(c/G);c=a+c%G;a!=b-b%G&&(c=b,d||(this.g|=131072));d?d=c:(this.o=c,d=b);return d} function Wc(a){a?a==G?this.g|=163840:a=db-a:this.g|=98304;return a}function Xc(a,b){var c=a-b;0>c&&(c+=J);Qc.call(this,c,b,a);return c}function Qc(a,b,c){a=Math.trunc(a/cb);b=Math.trunc(b/cb);c=Math.trunc(c/cb);var d=a^(a^b)&(b^c);this.g=this.g|(d&2?65536:0)|(d&1?32768:0)|((a^c)&(b^c)&2?131072:0)}function T(a,b){return((a/K|0)&(b/K|0))*K+((a&b)>>>0)}function U(a,b){return T(a,(~(b/K|0)&15)*K+(~b>>>0))}function V(a,b){return(a>>0)}function W(a,b){return(a/K|0|b/K|0)*K+((a|b)>>>0)}function X(a){return a>>0)}function Z(a){return(a/E|0)+(a&C)*E}function Ec(a,b,c){switch(a&384){case 0:b-=b&C;break;case 128:b=0;break;case 256:b=C*E;break;case 384:b=c>ab?C*E:0}return b}function vc(a,b,c){switch(a&384){case 0:b&=C;break;case 128:b=0;break;case 256:b=C;break;case 384:b=c>F?C:0}return b} function Sc(a,b){a[0]+=b[0];a[1]+=b[1];a[0]>=J&&(a[0]%=J,a[1]++)}function Rc(a,b){var c=a[1]-b[1];c||(c=a[0]-b[0]);return c}function Uc(a){a[1]%2&&(a[0]+=J);a[0]=Math.trunc(a[0]/2);a[1]=Math.trunc(a[1]/2)}function Tc(a){return!a[0]&&!a[1]}