aboutsummaryrefslogtreecommitdiff
path: root/luxc/src
diff options
context:
space:
mode:
authorEduardo Julian2017-03-12 20:16:34 -0400
committerEduardo Julian2017-03-12 20:16:34 -0400
commit913062dd2bc8559c44e0f07cdece404cc7f6791c (patch)
tree8112468e9629345e2da51995684a622bdc6eee44 /luxc/src
parentcb397b69bf5c5739353bffa938d74c3f2d404a02 (diff)
- Implemented natural decoding.
- Implemented the _lux_program statement.
Diffstat (limited to 'luxc/src')
-rw-r--r--luxc/src/lux/compiler/js/lux.clj83
-rw-r--r--luxc/src/lux/compiler/js/rt.clj138
2 files changed, 44 insertions, 177 deletions
diff --git a/luxc/src/lux/compiler/js/lux.clj b/luxc/src/lux/compiler/js/lux.clj
index 5c6039d2b..ffb75a3ef 100644
--- a/luxc/src/lux/compiler/js/lux.clj
+++ b/luxc/src/lux/compiler/js/lux.clj
@@ -381,78 +381,11 @@
)
(defn compile-program [compile ?body]
- (assert false "compile-program")
- ;; (|do [module-name &/get-module-name
- ;; ^ClassWriter *writer* &/get-writer]
- ;; (&/with-writer (doto (.visitMethod *writer* (+ Opcodes/ACC_PUBLIC Opcodes/ACC_STATIC) "main" "([Ljava/lang/String;)V" nil nil)
- ;; (.visitCode))
- ;; (|do [^MethodVisitor main-writer &/get-writer
- ;; :let [$loop (new Label)
- ;; $end (new Label)
- ;; _ (doto main-writer
- ;; ;; Tail: Begin
- ;; (.visitLdcInsn (->> #'&/$Nil meta ::&/idx int)) ;; I
- ;; (.visitInsn Opcodes/ACONST_NULL) ;; I?
- ;; (.visitLdcInsn &/unit-tag) ;; I?U
- ;; (.visitMethodInsn Opcodes/INVOKESTATIC "lux/LuxRT" "sum_make" "(ILjava/lang/Object;Ljava/lang/Object;)[Ljava/lang/Object;") ;; V
- ;; ;; Tail: End
- ;; ;; Size: Begin
- ;; (.visitVarInsn Opcodes/ALOAD 0) ;; VA
- ;; (.visitInsn Opcodes/ARRAYLENGTH) ;; VI
- ;; ;; Size: End
- ;; ;; Loop: Begin
- ;; (.visitLabel $loop)
- ;; (.visitLdcInsn (int 1)) ;; VII
- ;; (.visitInsn Opcodes/ISUB) ;; VI
- ;; (.visitInsn Opcodes/DUP) ;; VII
- ;; (.visitJumpInsn Opcodes/IFLT $end) ;; VI
- ;; ;; Head: Begin
- ;; (.visitInsn Opcodes/DUP) ;; VII
- ;; (.visitVarInsn Opcodes/ALOAD 0) ;; VIIA
- ;; (.visitInsn Opcodes/SWAP) ;; VIAI
- ;; (.visitInsn Opcodes/AALOAD) ;; VIO
- ;; (.visitInsn Opcodes/SWAP) ;; VOI
- ;; (.visitInsn Opcodes/DUP_X2) ;; IVOI
- ;; (.visitInsn Opcodes/POP) ;; IVO
- ;; ;; Head: End
- ;; ;; Tuple: Begin
- ;; (.visitLdcInsn (int 2)) ;; IVOS
- ;; (.visitTypeInsn Opcodes/ANEWARRAY "java/lang/Object") ;; IVO2
- ;; (.visitInsn Opcodes/DUP_X1) ;; IV2O2
- ;; (.visitInsn Opcodes/SWAP) ;; IV22O
- ;; (.visitLdcInsn (int 0)) ;; IV22OI
- ;; (.visitInsn Opcodes/SWAP) ;; IV22IO
- ;; (.visitInsn Opcodes/AASTORE) ;; IV2
- ;; (.visitInsn Opcodes/DUP_X1) ;; I2V2
- ;; (.visitInsn Opcodes/SWAP) ;; I22V
- ;; (.visitLdcInsn (int 1)) ;; I22VI
- ;; (.visitInsn Opcodes/SWAP) ;; I22IV
- ;; (.visitInsn Opcodes/AASTORE) ;; I2
- ;; ;; Tuple: End
- ;; ;; Cons: Begin
- ;; (.visitLdcInsn (->> #'&/$Cons meta ::&/idx int)) ;; I2I
- ;; (.visitLdcInsn "") ;; I2I?
- ;; (.visitInsn Opcodes/DUP2_X1) ;; II?2I?
- ;; (.visitInsn Opcodes/POP2) ;; II?2
- ;; (.visitMethodInsn Opcodes/INVOKESTATIC "lux/LuxRT" "sum_make" "(ILjava/lang/Object;Ljava/lang/Object;)[Ljava/lang/Object;") ;; IV
- ;; ;; Cons: End
- ;; (.visitInsn Opcodes/SWAP) ;; VI
- ;; (.visitJumpInsn Opcodes/GOTO $loop)
- ;; ;; Loop: End
- ;; (.visitLabel $end) ;; VI
- ;; (.visitInsn Opcodes/POP) ;; V
- ;; (.visitVarInsn Opcodes/ASTORE (int 0)) ;;
- ;; )
- ;; ]
- ;; _ (compile ?body)
- ;; :let [_ (doto main-writer
- ;; (.visitTypeInsn Opcodes/CHECKCAST &&/function-class)
- ;; (.visitInsn Opcodes/ACONST_NULL)
- ;; (.visitMethodInsn Opcodes/INVOKEVIRTUAL &&/function-class &&/apply-method (&&/apply-signature 1)))]
- ;; :let [_ (doto main-writer
- ;; (.visitInsn Opcodes/POP)
- ;; (.visitInsn Opcodes/RETURN)
- ;; (.visitMaxs 0 0)
- ;; (.visitEnd))]]
- ;; (return nil))))
- )
+ (|do [=body (compile ?body)
+ :let [program-js (str (str "var " (register-name 0) " = LuxRT.programArgs();")
+ (str "(" =body ")(null);"))]
+ eval? &/get-eval
+ ^StringBuilder buffer &&/get-buffer
+ :let [_ (when (not eval?)
+ (.append buffer ^String (str program-js "\n")))]]
+ (return "")))
diff --git a/luxc/src/lux/compiler/js/rt.clj b/luxc/src/lux/compiler/js/rt.clj
index 0ece93d6e..c022dd3bb 100644
--- a/luxc/src/lux/compiler/js/rt.clj
+++ b/luxc/src/lux/compiler/js/rt.clj
@@ -420,108 +420,6 @@
;; (.visitEnd)))]
;; nil))
-;; (let [+wrapper-class+ (&host-generics/->bytecode-class-name "java.lang.Long")]
-;; (defn ^:private compile-LuxRT-nat-methods [^ClassWriter =class]
-;; (|let [;; http://grepcode.com/file/repository.grepcode.com/java/root/jdk/openjdk/8u40-b25/java/lang/Long.java#677
-;; _ (let [$from (new Label)
-;; $to (new Label)
-;; $handler (new Label)
-
-;; $good-start (new Label)
-;; $short-enough (new Label)
-;; $bad-digit (new Label)
-;; $out-of-bounds (new Label)]
-;; (doto (.visitMethod =class (+ Opcodes/ACC_PUBLIC Opcodes/ACC_STATIC) "decode_nat" "(Ljava/lang/String;)Ljava/lang/Object;" nil nil)
-;; (.visitCode)
-;; (.visitTryCatchBlock $from $to $handler "java/lang/Exception")
-;; (.visitLabel $from)
-;; ;; Remove the + at the beginning...
-;; (.visitVarInsn Opcodes/ALOAD 0)
-;; (.visitLdcInsn (int 0))
-;; (.visitLdcInsn (int 1))
-;; (.visitMethodInsn Opcodes/INVOKEVIRTUAL "java/lang/String" "substring" "(II)Ljava/lang/String;")
-;; (.visitLdcInsn "+")
-;; (.visitMethodInsn Opcodes/INVOKEVIRTUAL "java/lang/Object" "equals" "(Ljava/lang/Object;)Z")
-;; (.visitJumpInsn Opcodes/IFNE $good-start)
-;; ;; Doesn't start with +
-;; (.visitMethodInsn Opcodes/INVOKESTATIC "lux/LuxRT" "make_none" "()Ljava/lang/Object;")
-;; (.visitInsn Opcodes/ARETURN)
-;; ;; Starts with +
-;; (.visitLabel $good-start)
-;; (.visitVarInsn Opcodes/ALOAD 0)
-;; (.visitLdcInsn (int 1))
-;; (.visitVarInsn Opcodes/ALOAD 0)
-;; (.visitMethodInsn Opcodes/INVOKEVIRTUAL "java/lang/String" "length" "()I")
-;; (.visitMethodInsn Opcodes/INVOKEVIRTUAL "java/lang/String" "substring" "(II)Ljava/lang/String;")
-;; (.visitVarInsn Opcodes/ASTORE 0) ;; Removed the + prefix...
-;; ;; Begin parsing processs
-;; (.visitVarInsn Opcodes/ALOAD 0)
-;; (.visitMethodInsn Opcodes/INVOKEVIRTUAL "java/lang/String" "length" "()I")
-;; (.visitLdcInsn (int 18))
-;; (.visitJumpInsn Opcodes/IF_ICMPLE $short-enough)
-;; ;; Too long
-;; ;; Get prefix...
-;; (.visitVarInsn Opcodes/ALOAD 0)
-;; (.visitLdcInsn (int 0))
-;; (.visitVarInsn Opcodes/ALOAD 0)
-;; (.visitMethodInsn Opcodes/INVOKEVIRTUAL "java/lang/String" "length" "()I")
-;; (.visitLdcInsn (int 1))
-;; (.visitInsn Opcodes/ISUB)
-;; (.visitMethodInsn Opcodes/INVOKEVIRTUAL "java/lang/String" "substring" "(II)Ljava/lang/String;")
-;; (.visitMethodInsn Opcodes/INVOKESTATIC "java/lang/Long" "parseLong" "(Ljava/lang/String;)J")
-;; (.visitInsn Opcodes/DUP2) ;; Clone prefix, for later...
-;; ;; Get last digit...
-;; (.visitVarInsn Opcodes/ALOAD 0)
-;; (.visitVarInsn Opcodes/ALOAD 0)
-;; (.visitMethodInsn Opcodes/INVOKEVIRTUAL "java/lang/String" "length" "()I")
-;; (.visitLdcInsn (int 1))
-;; (.visitInsn Opcodes/ISUB)
-;; (.visitMethodInsn Opcodes/INVOKEVIRTUAL "java/lang/String" "charAt" "(I)C")
-;; (.visitLdcInsn (int 10))
-;; (.visitMethodInsn Opcodes/INVOKESTATIC "java/lang/Character" "digit" "(CI)I")
-;; ;; Test last digit...
-;; (.visitInsn Opcodes/DUP)
-;; (.visitJumpInsn Opcodes/IFLT $bad-digit)
-;; ;; Good digit...
-;; ;; Stack: prefix::L, prefix::L, last-digit::I
-;; (.visitInsn Opcodes/I2L)
-;; ;; Build the result...
-;; swap2
-;; (.visitLdcInsn (long 10))
-;; (.visitInsn Opcodes/LMUL)
-;; (.visitInsn Opcodes/LADD) ;; Stack: prefix::L, result::L
-;; (.visitInsn Opcodes/DUP2_X2) ;; Stack: result::L, prefix::L, result::L
-;; swap2 ;; Stack: result::L, result::L, prefix::L
-;; (.visitMethodInsn Opcodes/INVOKESTATIC "lux/LuxRT" "_compareUnsigned" "(JJ)I")
-;; (.visitJumpInsn Opcodes/IFLT $out-of-bounds)
-;; ;; Within bounds
-;; ;; Stack: result::L
-;; &&/wrap-long
-;; (.visitMethodInsn Opcodes/INVOKESTATIC "lux/LuxRT" "make_some" "(Ljava/lang/Object;)Ljava/lang/Object;")
-;; (.visitInsn Opcodes/ARETURN)
-;; ;; Out of bounds
-;; (.visitLabel $out-of-bounds)
-;; (.visitMethodInsn Opcodes/INVOKESTATIC "lux/LuxRT" "make_none" "()Ljava/lang/Object;")
-;; (.visitInsn Opcodes/ARETURN)
-;; ;; Bad digit...
-;; (.visitLabel $bad-digit)
-;; (.visitMethodInsn Opcodes/INVOKESTATIC "lux/LuxRT" "make_none" "()Ljava/lang/Object;")
-;; (.visitInsn Opcodes/ARETURN)
-;; ;; 18 chars or less
-;; (.visitLabel $short-enough)
-;; (.visitVarInsn Opcodes/ALOAD 0)
-;; (.visitMethodInsn Opcodes/INVOKESTATIC "java/lang/Long" "parseLong" "(Ljava/lang/String;)J")
-;; &&/wrap-long
-;; (.visitMethodInsn Opcodes/INVOKESTATIC "lux/LuxRT" "make_some" "(Ljava/lang/Object;)Ljava/lang/Object;")
-;; (.visitInsn Opcodes/ARETURN)
-;; (.visitLabel $to)
-;; (.visitLabel $handler)
-;; (.visitMethodInsn Opcodes/INVOKESTATIC "lux/LuxRT" "make_none" "()Ljava/lang/Object;")
-;; (.visitInsn Opcodes/ARETURN)
-;; (.visitMaxs 0 0)
-;; (.visitEnd)))]
-;; nil)))
-
(def ^:private const-none (str "[0,null," &&/unit "]"))
(defn ^:private make-some [value]
(str "[1,''," value "]"))
@@ -867,6 +765,30 @@
"return '+'.concat(LuxRT.encodeI64(input));"
"}")
"})")
+ "decodeN64" (str "(function decodeN64(input) {"
+ (str "if(/^\\+\\d+$/.exec(input)) {"
+ (str "input = input.substring(1);")
+ (str "if(input.length <= 18) {"
+ ;; Short enough...
+ "return LuxRT.decodeI64(input);"
+ "}"
+ "else {"
+ ;; Too long
+ (str "var prefix = LuxRT.decodeI64(input.substring(0, input.length-1))[2];"
+ "var suffix = LuxRT.decodeI64(input.charAt(input.length-1))[2];"
+ "var total = LuxRT.addI64(LuxRT.mulI64(prefix,LuxRT.fromNumberI64(10)),suffix);"
+ (str "if(LuxRT.ltN64(total,prefix)) {"
+ (str "return " const-none ";")
+ "}"
+ "else {"
+ (str "return " (make-some "total") ";")
+ "}"))
+ "}")
+ "}"
+ "else {"
+ (str "return " const-none ";")
+ "}")
+ "})")
"divN64" (str "(function divN64(l,r) {"
(str "if(LuxRT.ltI64(r,LuxRT.ZERO)) {"
(str "if(LuxRT.ltN64(l,r)) {"
@@ -1128,6 +1050,18 @@
(str "return [0,null,ex.toString()];")
"}")
"})")
+ "programArgs" (str "(function programArgs() {"
+ (str "if(typeof process !== 'undefined' && process.argv) {"
+ (str (str "var result = " const-none ";")
+ "for(var idx = process.argv.length-1; idx >= 0; idx--) {"
+ (str "result = " (make-some "[process.argv[idx],result]") ";")
+ "}")
+ (str "return result;")
+ "}"
+ "else {"
+ (str "return " const-none ";")
+ "}")
+ "})")
})
(def LuxRT "LuxRT")