VaKeR CYBER ARMY
Logo of a company Server : Apache/2.4.41 (Ubuntu)
System : Linux absol.cf 5.4.0-198-generic #218-Ubuntu SMP Fri Sep 27 20:18:53 UTC 2024 x86_64
User : www-data ( 33)
PHP Version : 7.4.33
Disable Function : pcntl_alarm,pcntl_fork,pcntl_waitpid,pcntl_wait,pcntl_wifexited,pcntl_wifstopped,pcntl_wifsignaled,pcntl_wifcontinued,pcntl_wexitstatus,pcntl_wtermsig,pcntl_wstopsig,pcntl_signal,pcntl_signal_get_handler,pcntl_signal_dispatch,pcntl_get_last_error,pcntl_strerror,pcntl_sigprocmask,pcntl_sigwaitinfo,pcntl_sigtimedwait,pcntl_exec,pcntl_getpriority,pcntl_setpriority,pcntl_async_signals,pcntl_unshare,
Directory :  /usr/share/emscripten/src/experimental/

Upload File :
current_dir [ Writeable ] document_root [ Writeable ]

 

Current File : //usr/share/emscripten/src/experimental/simplifyGeneratedFunctionsDetection.diff
diff --git a/emscripten.py b/emscripten.py
index b698654..a7843c7 100755
--- a/emscripten.py
+++ b/emscripten.py
@@ -294,8 +294,6 @@ def emscript(infile, settings, outfile, libraries=[], compiler_engine=None,
   outfile.write(blockaddrsize(indexize(pre)))
   pre = None
 
-  #if DEBUG: outfile.write('// funcs\n')
-
   # forward
   forwarded_data = json.dumps(forwarded_json)
   forwarded_file = temp_files.get('.2.json').name
@@ -483,9 +481,14 @@ Runtime.stackRestore = function(top) { asm.stackRestore(top) };
   else:
     function_tables_defs = '\n'.join([table for table in last_forwarded_json['Functions']['tables'].itervalues()])
     outfile.write(function_tables_defs)
+
+  outfile.write('// EMSCRIPTEN_START_FUNCS\n')
+
   outfile.write(blockaddrsize(indexize(funcs_js)))
   funcs_js = None
 
+  outfile.write('// EMSCRIPTEN_END_FUNCS\n')
+
   outfile.write(indexize(post))
   if DEBUG: print >> sys.stderr, '  emscript: phase 3 took %s seconds' % (time.time() - t)
 
diff --git a/src/jsifier.js b/src/jsifier.js
index ff58ece..d6aa110 100644
--- a/src/jsifier.js
+++ b/src/jsifier.js
@@ -1587,12 +1587,6 @@ function JSify(data, functionsOnly, givenFunctions) {
 
     var shellParts = read(shellFile).split('{{BODY}}');
     print(shellParts[1]);
-    // Print out some useful metadata (for additional optimizations later, like the eliminator)
-    if (EMIT_GENERATED_FUNCTIONS) {
-      print('// EMSCRIPTEN_GENERATED_FUNCTIONS: ' + JSON.stringify(keys(Functions.implementedFunctions).filter(function(func) {
-        return IGNORED_FUNCTIONS.indexOf(func.ident) < 0;
-      })) + '\n');
-    }
 
     PassManager.serialize();
 
diff --git a/src/settings.js b/src/settings.js
index 1bfcf92..99c83f4 100644
--- a/src/settings.js
+++ b/src/settings.js
@@ -336,8 +336,6 @@ var EXPLICIT_ZEXT = 0; // If 1, generate an explicit conversion of zext i1 to i3
 
 var NECESSARY_BLOCKADDRS = []; // List of (function, block) for all block addresses that are taken.
 
-var EMIT_GENERATED_FUNCTIONS = 0; // whether to emit the list of generated functions, needed for external JS optimization passes
-
 // Compiler debugging options
 var DEBUG_TAGS_SHOWING = [];
   // Some useful items:
diff --git a/tools/js-optimizer.js b/tools/js-optimizer.js
index f2dc516..9fa038c 100644
--- a/tools/js-optimizer.js
+++ b/tools/js-optimizer.js
@@ -140,16 +140,6 @@ var UNDEFINED_NODE = ['unary-prefix', 'void', ['num', 0]];
 var TRUE_NODE = ['unary-prefix', '!', ['num', 0]];
 var FALSE_NODE = ['unary-prefix', '!', ['num', 1]];
 
-var GENERATED_FUNCTIONS_MARKER = '// EMSCRIPTEN_GENERATED_FUNCTIONS:';
-var generatedFunctions = null;
-function setGeneratedFunctions(metadata) {
-  var start = metadata.indexOf(GENERATED_FUNCTIONS_MARKER);
-  generatedFunctions = set(eval(metadata.substr(start + GENERATED_FUNCTIONS_MARKER.length)));
-}
-function isGenerated(ident) {
-  return ident in generatedFunctions;
-}
-
 function srcToAst(src) {
   return uglify.parser.parse(src);
 }
@@ -212,21 +202,9 @@ function traverse(node, pre, post, stack) {
   return result;
 }
 
-// Only walk through the generated functions
-function traverseGenerated(ast, pre, post, stack) {
-  assert(generatedFunctions);
-  traverse(ast, function(node) {
-    if (node[0] == 'defun' && isGenerated(node[1])) {
-      traverse(node, pre, post, stack);
-      return null;
-    }
-  });
-}
-
-function traverseGeneratedFunctions(ast, callback) {
-  assert(generatedFunctions);
+function traverseFunctions(ast, callback) {
   traverse(ast, function(node) {
-    if (node[0] == 'defun' && isGenerated(node[1])) {
+    if (node[0] == 'defun') {
       callback(node);
       return null;
     }
@@ -418,7 +396,7 @@ function simplifyExpressionsPre(ast) {
     var rerun = true;
     while (rerun) {
       rerun = false;
-      traverseGenerated(ast, function process(node, type, stack) {
+      traverse(ast, function process(node, type, stack) {
         if (type == 'binary' && node[1] == '|') {
           if (node[2][0] == 'num' && node[3][0] == 'num') {
             return ['num', node[2][1] | node[3][1]];
@@ -455,7 +433,7 @@ function simplifyExpressionsPre(ast) {
     }
 
     // &-related optimizations
-    traverseGenerated(ast, function(node, type) {
+    traverse(ast, function(node, type) {
       if (type == 'binary' && node[1] == '&' && node[3][0] == 'num') {
         if (node[2][0] == 'num') return ['num', node[2][1] & node[3][1]];
         var input = node[2];
@@ -489,7 +467,7 @@ function simplifyExpressionsPre(ast) {
 
     if (asm) {
       // optimize num >> num, in asm we need this here since we do not run optimizeShifts
-      traverseGenerated(ast, function(node, type) {
+      traverse(ast, function(node, type) {
         if (type == 'binary' && node[1] == '>>' && node[2][0] == 'num' && node[3][0] == 'num') {
           node[0] = 'num';
           node[1] = node[2][1] >> node[3][1];
@@ -505,7 +483,7 @@ function simplifyExpressionsPre(ast) {
     var rerun = true;
     while (rerun) {
       rerun = false;
-      traverseGenerated(ast, function(node, type) {
+      traverse(ast, function(node, type) {
         if (type == 'binary' && node[1] == '+') {
           if (node[2][0] == 'num' && node[3][0] == 'num') {
             rerun = true;
@@ -528,7 +506,7 @@ function simplifyExpressionsPre(ast) {
 
   // if (x == 0) can be if (!x), etc.
   function simplifyZeroComp(ast) {
-    traverseGenerated(ast, function(node, type) {
+    traverse(ast, function(node, type) {
       var binary;
       if (type == 'if' && (binary = node[1])[0] == 'binary') {
         if ((binary[1] == '!=' || binary[1] == '!==') && binary[3][0] == 'num' && binary[3][1] == 0) {
@@ -554,7 +532,7 @@ function simplifyExpressionsPre(ast) {
 // TODO: when shifting a variable, if there are other uses, keep an unshifted version too, to prevent slowdowns?
 function optimizeShiftsInternal(ast, conservative) {
   var MAX_SHIFTS = 3;
-  traverseGeneratedFunctions(ast, function(fun) {
+  traverseFunctions(ast, function(fun) {
     var funMore = true;
     var funFinished = {};
     while (funMore) {
@@ -999,7 +977,7 @@ function vacuum(ast) {
       } break;
     }
   }
-  traverseGeneratedFunctions(ast, function(node) {
+  traverseFunctions(ast, function(node) {
     vacuumInternal(node);
     simplifyNotComps(node);
   });
@@ -1021,7 +999,7 @@ function getStatements(node) {
 //   if (condition) { label == x } else ..
 // We can hoist the multiple block into the condition, thus removing code and one 'if' check
 function hoistMultiples(ast) {
-  traverseGeneratedFunctions(ast, function(node) {
+  traverseFunctions(ast, function(node) {
     traverse(node, function(node, type) {
       var statements = getStatements(node);
       if (!statements) return;
@@ -1135,7 +1113,7 @@ function hoistMultiples(ast) {
   //    if (..) { .. break|continue } else { .. }
   // to
   //    if (..) { .. break|continue } ..
-  traverseGenerated(ast, function(container, type) {
+  traverse(ast, function(container, type) {
     var statements = getStatements(container);
     if (!statements) return;
     for (var i = 0; i < statements.length; i++) {
@@ -1168,7 +1146,7 @@ function loopOptimizer(ast) {
   function passTwo(ast) {
     var neededDos = [];
     // Find unneeded labels
-    traverseGenerated(ast, function(node, type, stack) {
+    traverse(ast, function(node, type, stack) {
       if (type == 'label' && node[2][0] in LOOP) {
         // this is a labelled loop. we don't know if it's needed yet. Mark its label for removal for now now.
         stack.push(node);
@@ -1212,7 +1190,7 @@ function loopOptimizer(ast) {
     // We return whether another pass is necessary
     var more = false;
     // Remove unneeded labels
-    traverseGenerated(ast, function(node, type) {
+    traverse(ast, function(node, type) {
       if (type == 'label' && node[1][0] == '+') {
         more = true;
         var ident = node[1].substr(1);
@@ -1227,13 +1205,13 @@ function loopOptimizer(ast) {
     });
     // Remove unneeded one-time loops. We need such loops if (1) they have a label, or (2) they have a direct break so they are in neededDos.
     // First, add all labeled loops of this nature to neededDos
-    traverseGenerated(ast, function(node, type) {
+    traverse(ast, function(node, type) {
       if (type == 'label' && node[2][0] == 'do') {
         neededDos.push(node[2]);
       }
     });
     // Remove unneeded dos, we know who they are now
-    traverseGenerated(ast, function(node, type) {
+    traverse(ast, function(node, type) {
       if (type == 'do' && neededDos.indexOf(node) < 0) {
         assert(jsonCompare(node[1], ['num', 0]), 'Trying to remove a one-time do loop that is not one of our generated ones.;');
         more = true;
@@ -1407,7 +1385,7 @@ function denormalizeAsm(func, data) {
 //       we still need the eliminator? Closure? And in what order? Perhaps just
 //       closure simple?
 function registerize(ast) {
-  traverseGeneratedFunctions(ast, function(fun) {
+  traverseFunctions(ast, function(fun) {
     if (asm) var asmData = normalizeAsm(fun);
     // Add parameters as a first (fake) var (with assignment), so they get taken into consideration
     var params = {}; // note: params are special, they can never share a register between them (see later)
@@ -1671,7 +1649,7 @@ var ABORTING_ELIMINATOR_SCAN_NODES = set('new', 'object', 'function', 'defun', '
 
 function eliminate(ast, memSafe) {
   // Find variables that have a single use, and if they can be eliminated, do so
-  traverseGeneratedFunctions(ast, function(func, type) {
+  traverseFunctions(ast, function(func, type) {
     if (asm) var asmData = normalizeAsm(func);
     //printErr('eliminate in ' + func[1]);
 
@@ -2218,9 +2196,6 @@ var passes = {
 var src = read(arguments_[0]);
 var ast = srcToAst(src);
 //printErr(JSON.stringify(ast)); throw 1;
-var metadata = src.split('\n').filter(function(line) { return line.indexOf(GENERATED_FUNCTIONS_MARKER) >= 0 })[0];
-//assert(metadata, 'Must have EMSCRIPTEN_GENERATED_FUNCTIONS metadata');
-if (metadata) setGeneratedFunctions(metadata);
 
 arguments_.slice(1).forEach(function(arg) {
   passes[arg](ast);
diff --git a/tools/js_optimizer.py b/tools/js_optimizer.py
index 2fd2211..a253afb 100644
--- a/tools/js_optimizer.py
+++ b/tools/js_optimizer.py
@@ -41,17 +41,17 @@ def run_on_js(filename, passes, js_engine, jcache):
   if os.linesep != '\n':
     js = js.replace(os.linesep, '\n') # we assume \n in the splitting code
 
-  # Find suffix
-  suffix_marker = '// EMSCRIPTEN_GENERATED_FUNCTIONS'
-  suffix_start = js.find(suffix_marker)
-  suffix = ''
-  if suffix_start >= 0:
-    suffix = js[suffix_start:js.find('\n', suffix_start)] + '\n'
-    # if there is metadata, we will run only on the generated functions. If there isn't, we will run on everything.
-    generated = set(eval(suffix[len(suffix_marker)+1:]))
-
-  if not suffix and jcache:
-    # JCache cannot be used without metadata, since it might reorder stuff, and that's dangerous since only generated can be reordered
+  # Find markers
+  start_marker = '// EMSCRIPTEN_START_FUNCS\n'
+  end_marker = '// EMSCRIPTEN_END_FUNCS\n'
+  start = js.find(start_marker)
+  end = js.find(end_marker)
+  assert (start >= 0) == (end >= 0), 'must have both markers or neither'
+  have_markers = start >= 0
+  # if there are markers, we will run only on the generated functions. If there isn't, we will run on everything.
+
+  if not have_markers and jcache:
+    # JCache cannot be used without markers, since it might reorder stuff, and that's dangerous since only generated can be reordered
     # This means jcache does not work after closure compiler runs, for example. But you won't get much benefit from jcache with closure
     # anyhow (since closure is likely the longest part of the build).
     if DEBUG: print >>sys.stderr, 'js optimizer: no metadata, so disabling jcache'
@@ -59,27 +59,10 @@ def run_on_js(filename, passes, js_engine, jcache):
 
   # If we process only generated code, find that and save the rest on the side
   func_sig = re.compile('( *)function (_[\w$]+)\(')
-  if suffix:
-    pos = 0
-    gen_start = 0
-    gen_end = 0
-    while 1:
-      m = func_sig.search(js, pos)
-      if not m: break
-      pos = m.end()
-      indent = m.group(1)
-      ident = m.group(2)
-      if ident in generated:
-        if not gen_start:
-          gen_start = m.start()
-          assert gen_start
-        gen_end = js.find('\n%s}\n' % indent, m.end()) + (3 + len(indent))
-    assert gen_end > gen_start
-    pre = js[:gen_start]
-    post = js[gen_end:]
-    if 'last' in passes:
-      post = post.replace(suffix, '') # no need to write out the metadata - nothing after us needs it
-    js = js[gen_start:gen_end]
+  if have_markers:
+    pre = js[:start + len(start_marker)] # includes start marker
+    post = js[end:] # includes end marker
+    js = js[start + len(start_marker):end]
   else:
     pre = ''
     post = ''
@@ -95,7 +78,7 @@ def run_on_js(filename, passes, js_engine, jcache):
     if m:
       ident = m.group(2)
     else:
-      if suffix: continue # ignore whitespace
+      if have_markers: continue # ignore whitespace
       ident = 'anon_%d' % i
     assert ident
     funcs.append((ident, func))
@@ -131,7 +114,6 @@ def run_on_js(filename, passes, js_engine, jcache):
       temp_file = temp_files.get('.jsfunc_%d.js' % i).name
       f = open(temp_file, 'w')
       f.write(chunk)
-      f.write(suffix)
       f.close()
       return temp_file
     filenames = [write_chunk(chunks[i], i) for i in range(len(chunks))]
@@ -169,7 +151,6 @@ def run_on_js(filename, passes, js_engine, jcache):
       f.write(cached); # TODO: preserve order
       f.write('\n')
   f.write(post);
-  # No need to write suffix: if there was one, it is inside post which exists when suffix is there
   f.write('\n')
   f.close()
 

VaKeR 2022