comparison cbackend.js @ 177:76e3d4ae1746

Support more bitwise operations and function pointers in llMessages
author Mike Pavone <pavone@retrodev.com>
date Sat, 24 Aug 2013 09:54:47 -0700
parents 8d466c5a7dff
children ab7c142090a0
comparison
equal deleted inserted replaced
176:ab204751d1e7 177:76e3d4ae1746
32 } else { 32 } else {
33 return 'mcall(' + getMethodId(method) + '/* operator ' + method + ' */, 2, (object *)' + this.left.toC() + ', ' + this.right.toC() + ')\n'; 33 return 'mcall(' + getMethodId(method) + '/* operator ' + method + ' */, 2, (object *)' + this.left.toC() + ', ' + this.right.toC() + ')\n';
34 } 34 }
35 }; 35 };
36 op.prototype.toCLLExpr = function(vars) { 36 op.prototype.toCLLExpr = function(vars) {
37 var opmap = {'=': '==', 'xor': '^'}; 37 var opmap = {'=': '==', 'xor': '^', 'or': '|', 'and': '&'};
38 return this.left.toCLLExpr(vars) + (this.op in opmap ? opmap[this.op] : this.op) + this.right.toCLLExpr(vars); 38 return this.left.toCLLExpr(vars) + (this.op in opmap ? opmap[this.op] : this.op) + this.right.toCLLExpr(vars);
39 }; 39 };
40 op.prototype.toCLines = function(vars, needsreturn) { 40 op.prototype.toCLines = function(vars, needsreturn) {
41 return [ (needsreturn ? 'return (object *)' : '' ) + this.toCLLExpr(vars) + ';']; 41 return [ (needsreturn ? 'return (object *)' : '' ) + this.toCLLExpr(vars) + ';'];
42 }; 42 };
277 break; 277 break;
278 case 'struct:': 278 case 'struct:':
279 case 'struct': 279 case 'struct':
280 var receiver = this.receiver ? this.receiver : this.args[0]; 280 var receiver = this.receiver ? this.receiver : this.args[0];
281 return 'struct ' + receiver.toCTypeName(); 281 return 'struct ' + receiver.toCTypeName();
282 break;
283 case 'funptr:':
284 case 'funptr':
285 var rettype;
286 var firstArg;
287 if (this.receiver) {
288 rettype = this.receiver;
289 firstArg = 0;
290 } else {
291 rettype = this.args[0];
292 firstArg = 1;
293 }
294 var argtypes = '';
295 for (var i = firstArg; i < this.args.length; i++) {
296 if (argtypes) {
297 argtypes += ', '
298 }
299 argtypes += this.args[i].toCTypeName();
300 }
301 return [rettype.toCTypeName() + '(*', ')(' + argtypes + ')'];
282 break; 302 break;
283 default: 303 default:
284 throw new Error('invalid use of funcall expression where a C type name is expected'); 304 throw new Error('invalid use of funcall expression where a C type name is expected');
285 } 305 }
286 }; 306 };
373 return args[0].toCLLExpr(vars) + '[' + args[1].toCLLExpr(vars) + ']'; 393 return args[0].toCLLExpr(vars) + '[' + args[1].toCLLExpr(vars) + ']';
374 case 'set': 394 case 'set':
375 return args[0].toCLLExpr(vars) + '[' + args[1].toCLLExpr(vars) + '] = ' + args[2].toCLLExpr(vars); 395 return args[0].toCLLExpr(vars) + '[' + args[1].toCLLExpr(vars) + '] = ' + args[2].toCLLExpr(vars);
376 case 'not': 396 case 'not':
377 return '!(' + args[0].toCLLExpr(vars) + ')'; 397 return '!(' + args[0].toCLLExpr(vars) + ')';
398 case 'castTo':
399 return '((' + args[1].toCTypeName() + ')(' + args[0].toCLLExpr(vars) + '))';
378 case 'mcall': 400 case 'mcall':
379 if (args[0] instanceof symbol) { 401 if (args[0] instanceof symbol) {
380 args[0] = new intlit(getMethodId(args[0].name)); 402 args[0] = new intlit(getMethodId(args[0].name));
381 } 403 }
382 default: 404 default:
484 includes += '#include ' + file + '\n'; 506 includes += '#include ' + file + '\n';
485 } 507 }
486 var objdef = 'typedef struct ' + this.name + ' {\n\tobject header;\n'; 508 var objdef = 'typedef struct ' + this.name + ' {\n\tobject header;\n';
487 for (var i in this.properties) { 509 for (var i in this.properties) {
488 if (this.properties[i] instanceof Array) { 510 if (this.properties[i] instanceof Array) {
489 objdef += '\t' + this.properties[i][1] + ' ' + this.properties[i][0] + ';\n'; 511 if (this.properties[i][1] instanceof Array) {
512 objdef += '\t' + this.properties[i][1][0] + this.properties[i][0] + this.properties[i][1][1] + ';\n';
513 } else {
514 objdef += '\t' + this.properties[i][1] + ' ' + this.properties[i][0] + ';\n';
515 }
490 } else { 516 } else {
491 objdef += '\tobject * ' + this.properties[i] + ';\n' 517 objdef += '\tobject * ' + this.properties[i] + ';\n'
492 } 518 }
493 } 519 }
494 objdef += '} ' + this.name + ';\nobj_meta ' + this.name + '_meta;\n'; 520 objdef += '} ' + this.name + ';\nobj_meta ' + this.name + '_meta;\n';
505 } 531 }
506 if (i in this.slots) { 532 if (i in this.slots) {
507 slotdefs += 'object * ' + this.name + '_slot_' + i + '(uint32_t method_id, uint32_t num_params, object * oself, va_list args) {\n\t' + 533 slotdefs += 'object * ' + this.name + '_slot_' + i + '(uint32_t method_id, uint32_t num_params, object * oself, va_list args) {\n\t' +
508 this.name + ' *self = (' + this.name + ' *)oself;\n'; 534 this.name + ' *self = (' + this.name + ' *)oself;\n';
509 for (var varname in this.slotvars[i]) { 535 for (var varname in this.slotvars[i]) {
510 slotdefs += '\t' + this.slotvars[i][varname] + ' ' + varname + ';\n'; 536 if (this.slotvars[i][varname] instanceof Array) {
537 slotdefs += '/*foo*/\t' + this.slotvars[i][varname][0] + ' ' + varname + this.slotvars[i][varname][1] + ';\n';
538 } else {
539 slotdefs += '/*bar*/\t' + this.slotvars[i][varname] + ' ' + varname + ';\n';
540 }
511 } 541 }
512 if (this.slots[i].length == 1) { 542 if (this.slots[i].length == 1) {
513 slotdefs += '\tif (method_id == ' + this.slots[i][0][0] + ') { /* ' + this.slots[i][0][2] + '*/\n' + 543 slotdefs += '\tif (method_id == ' + this.slots[i][0][0] + ') { /* ' + this.slots[i][0][2] + '*/\n' +
514 '\t\t' + this.slots[i][0][1] + '\n' + 544 '\t\t' + this.slots[i][0][1] + '\n' +
515 '\t}\n' + 545 '\t}\n' +
577 } 607 }
578 importsyms.push(el); 608 importsyms.push(el);
579 }); 609 });
580 me.addImport(importsyms, messages[i].args[1]); 610 me.addImport(importsyms, messages[i].args[1]);
581 } else if(messages[i].name == 'llProperty:withType:' && messages[i].args.length == 2) { 611 } else if(messages[i].name == 'llProperty:withType:' && messages[i].args.length == 2) {
582 me.addProperty(messages[i].args[0].name, null, messages[i].args[1].toCTypeName()) 612 me.addProperty(messages[i].args[0].name, null, messages[i].args[1].toCTypeName());
583 } else if(messages[i].name == 'llMessage:withVars:andCode:' && messages[i].args.length == 3) { 613 } else if(messages[i].name == 'llMessage:withVars:andCode:' && messages[i].args.length == 3) {
584 var msgname = messages[i].args[0].name 614 var msgname = messages[i].args[0].name
585 var rawvars = messages[i].args[1].expressions; 615 var rawvars = messages[i].args[1].expressions;
586 var vars = {}; 616 var vars = {};
587 for(var v in rawvars) { 617 for(var v in rawvars) {