Commit 0c542be0 authored by Vladimir Sedach's avatar Vladimir Sedach

Revised obfuscation facility, added its description to the reference, and added more unit tests.

parent 5e74b5ce
......@@ -1048,7 +1048,7 @@ a-variable => aVariable
;;;t \index{namespace}
;;;t \index{PS-PACKAGE-PREFIX}
;;; (setf (PS-PACKAGE-PREFIX lisp-package) string)
; (setf (PS-PACKAGE-PREFIX package-designator) string)
;;; Although JavaScript does not offer namespacing or a package
;;; system, ParenScript does provide a namespace mechanism for
......@@ -1060,17 +1060,38 @@ a-variable => aVariable
;;; a particular package receive a prefix when translated to
;;; JavaScript with the `PS-PACKAGE-PREFIX' place.
(lisp (defpackage "MY-LIBRARY"
(defpackage "MY-LIBRARY"
(:use #:parenscript))
(setf (ps-package-prefix :my-library) "my_library_"))
=> 'my_library_'
(setf (ps-package-prefix :my-library) "my_library_")
(defun my-library::library-function (x y)
(return (+ x y)))
=> function my_library_libraryFunction(x, y) {
-> function my_library_libraryFunction(x, y) {
return x + y;
;;;# Identifier obfuscation
;;;t \index{obfuscation}
;;;t \index{identifiers}
; (OBFUSCATE-PACKAGE package-designator)
; (UNOBFUSCATE-PACKAGE package-designator)
;;; Similar to the namespace mechanism, ParenScript provides a
;;; facility to generate obfuscated identifiers in certain Lisp
;;; packages.
(defpackage "OBFUSCATE-ME")
(obfuscate-package :obfuscate-me)
(defun obfuscate-me::library-function2 (a b obfuscate-me::foo)
(+ a (my-library::library-function b obfuscate-me::foo)))
;;; The obfuscation and namespace facilities can be used on packages
;;; at the same time.
;;;# The ParenScript Compiler
;;;t \index{compiler}
;;;t \index{ParenScript compiler}
......@@ -10,19 +10,22 @@
(otherwise (symbol-name symbol))))
;;; Symbol obfuscation
(defvar *obfuscate-identifiers* nil)
(defvar *obfuscation-table* (make-hash-table))
(defparameter *obfuscation-table* (make-hash-table))
(defun obfuscate-package (package-designator)
(setf (gethash (find-package package-designator) *obfuscation-table*) (make-hash-table)))
(defun obfuscated-symbol (symbol)
(or (gethash symbol *obfuscation-table*)
(setf (gethash symbol *obfuscation-table*) (string (gensym)))))
(defun unobfuscate-package (package-designator)
(remhash (find-package package-designator) *obfuscation-table*))
;;; Interface for printing identifiers
(defun maybe-obfuscate-symbol (symbol)
(let ((obfuscated-symbol-table (gethash (symbol-package symbol) *obfuscation-table*)))
(if obfuscated-symbol-table
(or (gethash symbol obfuscated-symbol-table)
(setf (gethash symbol obfuscated-symbol-table) (ps-gensym "G")))
(defvar *package-prefix-style* :prefix
"Determines how package symbols are serialized to JavaScript identifiers. NIL for
no prefixes. :prefix to prefix variables with something like packagename_identifier.")
;;; Interface for printing identifiers
(defvar *package-prefix-table* (make-hash-table))
......@@ -32,8 +35,7 @@ designated package when translating ParenScript code."
`(gethash (find-package ,package) *package-prefix-table*))
(defun js-translate-symbol (symbol)
(cond (*obfuscate-identifiers* (obfuscated-symbol symbol))
((and (eql *package-prefix-style* :prefix) (ps-package-prefix (symbol-package symbol)))
(format nil "~A~A" (ps-package-prefix (symbol-package symbol)) (symbol-to-js symbol)))
(t (symbol-to-js symbol))))
(let ((possibly-obfuscated-symbol (maybe-obfuscate-symbol symbol)))
(if (ps-package-prefix (symbol-package symbol))
(format nil "~A~A" (ps-package-prefix (symbol-package symbol)) (symbol-to-js possibly-obfuscated-symbol))
(symbol-to-js possibly-obfuscated-symbol))))
......@@ -176,9 +176,9 @@
;; naming and namespaces
;; deprecated interface
......@@ -6,7 +6,7 @@
(defvar *ps-gensym-counter* 0)
(defun ps-gensym (&optional (prefix "_js"))
(make-symbol (format nil "~A-~A" prefix (incf *ps-gensym-counter*))))
(make-symbol (format nil "~A~A" prefix (incf *ps-gensym-counter*))))
(defmacro with-ps-gensyms (symbols &body body)
"Evaluate BODY with SYMBOLS bound to unique ParenScript identifiers.
......@@ -5,6 +5,40 @@
(in-suite package-system-tests)
(defpackage "MY-LIBRARY"
(:use #:parenscript))
(setf (ps-package-prefix :my-library) "my_library_")
(test-ps-js lib-function1
(defun my-library::library-function (x y)
(return (+ x y)))
"function my_library_libraryFunction(x, y) {
return x + y;
(defpackage "OBFUSCATE-ME")
(obfuscate-package :obfuscate-me)
(test-ps-js obfuscation1
(defun obfuscate-me::library-function2 (a b obfuscate-me::foo)
(+ a (my-library::library-function b obfuscate-me::foo)))
"function g2(a, b, g3) {
a + my_library_libraryFunction(b, g3);
(obfuscate-package "OBFUSCATE-AND-PREFIX")
(setf (ps-package-prefix "OBFUSCATE-AND-PREFIX") "__FOO___")
(test-ps-js obfuscate-and-prefix
(defun obfuscate-and-prefix::some-function (a obfuscate-and-prefix::b my-library::d)
(* a
(obfuscate-me::library-function2 obfuscate-and-prefix::b a)
(my-library::library-function my-library::d obfuscate-and-prefix::b)))
"function __FOO___g2(a, __FOO___g3, my_library_d) {
a * g2(__FOO___g3, a) * my_library_libraryFunction(my_library_d, __FOO___g3);
(defpackage "PSTSTPKG"
(:use #:parenscript))
......@@ -513,16 +513,3 @@ = _js1;")
+ ' looks like this.</div>';
(test-ps-js the-parenscript-namespace-system-1
(lisp (defpackage "MY-LIBRARY"
(:use #:parenscript))
(setf (ps-package-prefix :my-library) "my_library_"))
(test-ps-js the-parenscript-namespace-system-2
(defun my-library::library-function (x y)
(return (+ x y)))
"function my_library_libraryFunction(x, y) {
return x + y;
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment