GithubHelp home page GithubHelp logo

shirok / gauche Goto Github PK

View Code? Open in Web Editor NEW
793.0 73.0 81.0 85.9 MB

Scheme Scripting Engine

License: Other

Shell 4.92% Scheme 60.35% C++ 0.62% C 32.19% Makefile 0.64% CMake 0.21% Assembly 0.02% CSS 0.02% M4 0.98% Roff 0.04% Emacs Lisp 0.01%
scheme r7rs-scheme

gauche's Issues

Export-time renaming, import-time renaming and intermediate module don't go along

gosh> (use gauche.base :except (div) :rename ((gauche:import import)))
*** ERROR: during processing :rename clause: binding of gauche:import isn't exported from #<module #f$gauche.base @0x237d150>
    While compiling "(standard input)" at line 1: (use gauche.base :except (div) :rename ((gauche:import import)))
Stack Trace:
_______________________________________
  0  (eval expr env)
        at "/usr/share/gauche-0.9/0.9.5/lib/gauche/interactive.scm":282

The :except option creates implicit intermediate module, but it seems to lose export-time renaming
of import in gauche.base, causing binding check of :rename option fail.

segmentation fault for (cond (1 2 . 3))

When I evaluate (cond (1 2 . 3)) in the gosh, gosh stoppes running due to segmentation fault.

version: Gauche scheme shell, version 0.9.4 [utf-8,pthreads], x86_64-unknown-linux-gnu

Enhance 'maybe' stub type

Currently, only pointer types can be qualified as 'maybe' in stub declaration. We might be able to extend it to immediate types in cproc arg list, if the fallback values are provided. It's especially useful for optional and keyword args.

Example: (define-cproc foo (:optional (x::<fixnum>? -1) (y::<fixnum>? -1)) ...)

The caller can call (foo #f 3) and x receives -1. This allows the caller to be agnostic about x's default value while providing y's value.

Can't rebuild gauche from source

Current (2085186) Unicode table generator src/gen-unicode.scm will not works with previous released version Gauche 0.9.4.
Because gflatten is not available in version 0.9.4 of gauche.generator module.

This error will breaks re-building Gauche from source code.

*** ERROR: unbound variable: gflatten
Stack Trace:
_______________________________________
  0  (gflatten (gmap (^_ items) (giota c)))
        At line 720 of "../lib/text/unicode/ucd.scm"

Design for scsh/shell-like process control

I'm implementing "||", "&&" and "|" shell syntax in scheme. Maybe it could become part of gauche.process. Before I waste your time with my code. I'd like to check what would be a good design for this. What I have in mind is this. A bit higher level than run-process, but still not the same as scsh. But hopefully we can make scsh wrapper more easily with these.

Process Form

A process is represented by

  • A single string

  • A single symbol

  • A list of strings or symbols (could be intermixed)

  • A list, where the first item is in either three above forms, followed by a list of run-process-like redirects, e.g.

    ((ls) (> 1 "out") (< 0 "in"))

Process execution

The procedure "run-pf&" takes one process form (pf), executes it and return the process object immediately. This is simply a wrapper around run-process that can handle process forms.

The procedure "run-pf" is like run-pf& except that it waits for the process to terminate and returns the exit code. If the process is signaled, the exit code is in 128+ range like how unix shell does it. Anything that can't be converted to exit code (e.g. process-wait fails) results in an exception.

run-pf can take more than argument too. In that case it executes processes sequentially like scheme "begin" form and returns exit code of the last process.

The procedure "run-and" takes 1+ arguments as process form and executes them in sequence so long as their exit codes are zero, i.e. "&&" syntax. It returns exit code of the last executed process. "run-or" is similar, for "||" syntax.

Redirection is generally ok for run-pf, run-and and run-or, except redirection to ports, for obvious reasons.

Piping

The procedure run-pipe+& has the following form

(define (run-pipe+& first-redir last-redir connect-list . pf/rest))

first-redir and last-redir are two lists of extra redirections for the first and the last process. They are in the same form that of :redirects keyword from run-process. This allows us to setup stdin of the first process, or stdout of the last process.

connect-list specifies how to connect two consecutive processes together. It's the exact same form from scsh's fork/pipe+. For example "((1 2 0) (3 3))" says redirect both stdout and stderr of the first process to stdin of the second one, and redirect fd 3 of the first to 3 of the second.

run-pipe+& immediately returns a list of process objects. For example, we could offload complex processing to some oustide command with

(run-pipe+& '((< 0 input)) '((> 1 output)) '((1 0)) '(cmd1) '(cmd2) '(cmd3))

Then retrieve the two input/output ports from the relevant process objects and start piping.

From that we have a few convenient wrappers:

  • run-pipe+ waits for all processes to finish before return, and returns exit code of the last process in pipe. It does not take first-redir/last-redir either
  • run-pipe is run-pipe+ with default connection-list ((1 0))

Build error

Under Arch Linux 64 bit the master branch does not compile since very recently.

TARGETLIB=pwd gcc -march=x86-64 -mtune=generic -O2 -pipe -fstack-protector-strong --param=ssp-buffer-size=4 -fPIC -Wl,--rpath=pwd -L. -Wl,-O1,--sort-common,--as-needed,-z,relro -Wl,--soname,libgauche-0.9.so.0.5 -shared -o libgauche-0.9.so box.o core.o vm.o compaux.o macro.o code.o error.o class.o prof.o collection.o boolean.o char.o string.o list.o hash.o treemap.o bits.o port.o write.o read.o vector.o weak.o symbol.o gloc.o compare.o regexp.o signal.o parameter.o module.o proc.o number.o bignum.o load.o paths.o lazy.o repl.o autoloads.o system.o compile.o libalpha.o libbool.o libchar.o libcode.o libcmp.o libdict.o libeval.o libexc.o libfmt.o libio.o liblazy.o liblist.o libmisc.o libmod.o libnum.o libobj.o libomega.o libproc.o librx.o libsrfis.o libstr.o libsym.o libsys.o libvec.o libgc_pic.a -latomic_ops -ldl -lcrypt -lutil -lrt -lm -lpthread
TARGETLIB=pwd /bin/bash ./makeverslink libgauche-0.9.so
./makeverslink: line 29: cd: /home/haawda/paketierung/meine_Pakete/gauche-git/pkg/gauche-git/home/haawda/paketierung/meine_Pakete/gauche-git/src/Gauche/src: No such file or directory
Makefile:346: recipe for target 'libgauche-0.9.so' failed
make[1]: *** [libgauche-0.9.so] Error 1
make[1]: Leaving directory '/home/haawda/paketierung/meine_Pakete/gauche-git/src/Gauche/src'
Makefile:39: recipe for target 'all' failed
make: *** [all] Error 1
==> ERROR: A failure occurred in build().
Aborting...

Makeinfo cannot compile gauche-refe.texi (tested with makeinfo 5.2 and 6.x from svn)

Hello,

I get the following:

if test Xmakeinfo != X -a Xgzip != X; then \
  env LANG=C makeinfo --no-warn gauche-refe.texi; \
  rm -rf gauche-refe.info*.gz; \
  gzip gauche-refe.info gauche-refe.info-[0-9]*; \
fi
gauche-refe.texi:520: @xref reference to nonexistent node `Hygienic Macros'

Creating the pdf works, so pdftex has no such problem. Maybe I should report thi to the texinfo mailing list?

Compilation failed on windows + MinGW when configured with '--enable-multibyte=' sjis or euc-jp

on 0.9.5 pre1.
because of some typo...
[src/system.c]

diff --git a/src/system.c b/src/system.c
index 7069601..7bda1d1 100644
--- a/src/system.c
+++ b/src/system.c
@@ -2307,13 +2307,13 @@ void Scm_SetEnv(const char *name, const char *value, int overwrite)

     ScmObj sname = Scm_MakeString(name, -1, -1, SCM_STRING_COPYING);

-    int result = 0;
-    chat *prev_mem = NULL;
+    int r = 0;
+    char *prev_mem = NULL;

     (void)SCM_INTERNAL_MUTEX_LOCK(env_mutex);
     if (overwrite || getenv(name) == NULL) {
-        result = putenv(nameval);
-        if (result >= 0) {
+        r = putenv(nameval);
+        if (r >= 0) {

support more $TERM in text.line-edit

I'm very happy to see Gauche starts to have some line editing capability. But it does not work out of the box for me because tmux set $TERM to screen. I suppose we can just add that to the recognized $TERM for now (it worked ok for me when I forced TERM to xterm, for example). I don't know if you can talk to screen/tmux to find out the actual term type, but I guess it's not that important.

Please also "support" rxvt-256color, by maybe relaxing the /^rxvt$/ pattern a a little bit.

Hope to see line editing in gosh soon!

port-tell is not the same as ftell

When opening a file in append mode, port-tell returns 0, even when the file has contents in it. Then after writting data to the file, the result of port-tell increases the same as the amount of bytes written, but this is still relative to 0 (so, after opening a file with 40 bytes on it, and writing 4 bytes more, port-tell returns 4 instead of 44).

When using ftell in C, the result of calling it after opening a file in append mode, is the amount of bytes in the file.

I see that port-tell in Gauche is defined in terms of port-seek (which I assume is fseek), but the result of this is that the behaviour is a bit surprising:

(define (port-tell p) (port-seek p 0 SEEK_CUR))

If an (port-seek port 0 SEEK_END) call is made to explicitly set the stream position at the end, then the results of calling port-tell start being the expected ones.

Example Scheme program to reproduce this.

(define f (open-output-file "/tmp/append-test" :if-exists :append :if-does-not-exist :create))

(display (port-tell f)) ;; displays 0
(newline)
(display "1234" f)
(display (port-tell f)) ;; displays 4
(newline)
(port-seek f 0 SEEK_END)
(display (port-tell f)) ;; displays 44 (file started with 40 bytes)
(newline)
(display "5678" f)
(display (port-tell f)) ;; displays 48 as expected
(newline)

(close-output-port f)

Example C program to see the behaviour of using ftell after opening a file in append mode:

#include <stdio.h>

int main() {
  FILE *f = fopen("/tmp/append-test", "a");
  printf("%ld\n", ftell(f));
  fclose(f);
  return 0;
}

Assertion failure with partcont

% gosh -V
Gauche scheme shell, version 0.9.5 [utf-8,pthreads], x86_64-apple-darwin16.0.0

Running a following program causes an assertion failure.

% cat cont.scm
(use gauche.partcont)

(define (f args)
  (reset
    (let ((in (shift k
                (call-with-input-file (cadr args) k))))
      (write (read-char in))
      (newline)
      0)))

;; OK
(f (command-line))
;; -| #<eof>

(define (main args)
  (f args))
;; -| #<eof>
;; --> "./vminsn.scm", line 1370: Assertion failed: SCM_PAIRP((vm)->handlers)

It seems OK to call f, a function using shift/reset, at the top-level, but causes an assertion failure to call it from main.

% gosh cont.scm /dev/null
#<eof>
#<eof>
"./vminsn.scm", line 1370: Assertion failed: SCM_PAIRP((vm)->handlers)
VM 0x101182c80 -----------------------------------------------------------
   pc: 0x100276da8 (0000000e)
   sp: 0x101184020  base: 0x101184000  [0x101184000-0x101197880]
 argp: 0x101184020
 val0: 0
 envs:
   0x101184008 #f
       up=0x1013da2e0 size=1
       [ (0) ]
   0x1013da2e0 #f
       up=0x1013dfae8 size=2
       [ #<closure ((call-with-input-file #f #f) . #f)> #<closure ((call-with-input-file #f #f) . #f)> ]
   0x1013dfae8 #f
       up=0x1013dfac8 size=1
       [ #<closure ((#f #:G1331) code fmt args)> ]
   0x1013dfac8 #f
       up=0x1013da378 size=1
       [ #<iport /dev/null 0x1011ddc00> ]
   0x1013da378 (call-with-input-file filename proc . flags)
       up=0x0 size=3
       [ () #<closure ((call/pc #f #f) . args)> "/dev/null" ]
conts:
   0x1013dc010
              env = 0x1001c0628
             size = 2
               pc = {cproc 0x100020870}
             base = 0x100272df0
   0x1013da420
              env = 0x0
             size = 0
               pc = 0x1002c7590 (00000000)
             base = 0x1013d6c60
   0x1013da3f0
              env = 0x0
             size = 0
               pc = 0x1002c7590 (00000000)
             base = 0x0
C stacks:
  0x7fff5fbfeee0: prev=0x7fff5fbff130, cont=0x1013da420
  0x7fff5fbff130: prev=0x0, cont=0x1013da3f0
Escape points:
dynenv: ()
Code:
=== main_code (name=#f, code=0x100276d08, size=48, const=0 stack=16):
signatureInfo: ()
     0 CLOSURE #<lambda 0>
     2 PUSH 
     3 CLOSURE #<lambda 1>
     5 PUSH-LOCAL-ENV(2) 
     6 PRE-CALL(0) 10
     8 LREF0 
     9 LOCAL-ENV-CALL(0) 
    10 LREF0-PUSH 
    11 LREF1 
    12 PUSH-HANDLERS 
    13 PRE-CALL(1) 18
    15 LREF20-PUSH 
    16 LREF(3,1) 
    17 CALL(1) 
    18 TAIL-RECEIVE(0,1) 
    19 POP-HANDLERS 
    20 PRE-CALL(0) 24
    22 LREF11 
    23 LOCAL-ENV-CALL(0) 
    24 PRE-CALL(0) 30
    26 GREF-PUSH #<gloc scheme#values inlinable>
    28 LREF0 
    29 TAIL-APPLY(2) 
    30 POP-LOCAL-ENV 
    31 POP-LOCAL-ENV 
    32 TAIL-RECEIVE(0,1) 
    33 LREF20 
    34 BF 43
    36 PRE-CALL(1) 43
    38 LREF20-PUSH 
    39 GREF-CALL(1) #<gloc scheme#close-input-port>
    41 JUMP 43
    43 GREF-PUSH #<gloc scheme#values inlinable>
    45 LREF0 
    46 TAIL-APPLY(2) 
    47 RET 
=== closure:1 (name=#f, code=0x100276ce0, size=5, const=0 stack=4):
signatureInfo: ()
     0 CLOSURE #<lambda 2>
     2 PUSH-GREF-TAIL-CALL(1) #<gloc gauche#exit-handler>
     4 RET 
=== closure:2 (name=#f, code=0x100276c60, size=16, const=0 stack=10):
signatureInfo: (code fmt args)
     0 LREF20 
     1 BF 10
     3 PRE-CALL(1) 10
     5 LREF20-PUSH 
     6 GREF-CALL(1) #<identifier gauche.internal#close-input-port.1221660>
     8 JUMP 10
    10 LREF2-PUSH 
    11 LREF1-PUSH 
    12 LREF0-PUSH 
    13 LREF10 
    14 TAIL-CALL(3) 
    15 RET 
=== closure:0 (name=#f, code=0x100276c40, size=4, const=0 stack=4):
signatureInfo: ()
     0 LREF0-PUSH 
     1 GREF-TAIL-CALL(1) #<gloc gauche#exit-handler>
     3 RET 
exitting...

MinGW build failure

This is FYI issue. Just close this issue if satisfied.

Current master branch will breaks MinGW build because of too old autoconf.

I think current MinGW is outdated. But I found there are MinGW-W64 ( http://mingw-w64.org/ )
and MSYS2 ( http://msys2.github.io/ ).

I think MinGW-W64 and MSYS2 will works well for current master branch.

gauche.process - redirecting both stdout and stderr to the same port

This program should demonstrate it. I create a new process and want to redirect both stdout and stderr to the same port, but it does not work. I think run-process could check if a pipe is already associated with the symbol 'abc' and reuse it. Though I guess there may be some hairy details I didn't see.

(use gauche.process)
(use file.util)

(with-output-to-file "test.sh"
  (lambda ()
    (print "#!/bin/sh")
    (print "echo stdout")
    (print "echo stderr >&2")))
(sys-chmod "test.sh" #o755)
(let ((p (run-process "./test.sh" :redirects '((> 2 abc) (> 1 abc)))))
  (print (port->string (process-output p 'abc))))

(import (gauche base)) fails from R7RS code

I'm building an R7RS library and I need to import Gauche's hash-table procedures. According to the documentation, in order to import Gauche's builtins into R7RS code, one must import (gauche base). Unfortunately this seems to fail. I'm using a fresh copy of Gauche built from the master branch this morning.

I run $ gosh -r7, then from the REPL I attempt to evaluate (import (gauche base)). Instead of succeeding, it fails with the following error:

gosh[r7rs.user]> (import (gauche base))
*** ERROR: cannot find "gauche/base" in ("/usr/local/share/gauche-0.9/site/lib" "/usr/local/share/gauche-0.9/0.9.5_pre1/lib" "/usr/local/share/gauche/site/lib" "/usr/local/share/gauche/0.9/lib")
    While compiling "(standard input)" at line 15: (import (gauche base))
Stack Trace:
_______________________________________
  0  (eval expr env)
        At line 220 of "/usr/local/share/gauche-0.9/0.9.5_pre1/lib/gauche/interactive.scm"

Is this a bug, or is there something else I am missing? Thanks.

Parameterize doesn't rewind correctly

When an error is thrown within guard procedure.

Reported by Joo ChurlSoo. Here's a sample session exhibiting the bug.

gosh> (use gauche.parameter)

gosh>
(define a (make-parameter 1 number->string))
(define b (make-parameter 2 number->string))
a
gosh> b
gosh> (list (a) (b))
("1" "2")
gosh> (parameterize ((a 10) (b 20) (a 30) (b 40)) (list (a) (b)))
("30" "40")
gosh> (list (a) (b))
("10" "20")
gosh> (a 1) (b 2)
"10"
gosh> "20"
gosh> (list (a) (b))
("1" "2")
gosh> (parameterize ((a 10) (b 20) (a 30) (b 'ab)) (list (a) (b)))
*** ERROR: number required: ab
Stack Trace:


0 (P L)
[unknown location]
1 (^ () (set! S (P L)) (set! S (P L)) (set! S (P L)) (set! S (P L)))
[unknown location]
2 (eval expr env)
At line 179 of "c:\tilde\gauche\share\gauche-0.9\0.9.4\lib/gauche/interactive.scm"
gosh> (list (a) (b))
("30" "20")
gosh> (let ((f (make-parameter 'a))
(path '())
(g (make-parameter 'g))
(c #f))
(let ((add (lambda () (set! path (cons (f) path)))))
(add)
(parameterize ((f 'b)
(g (call-with-current-continuation
(lambda (c0) (set! c c0) 'c))))
(add) (f (g)) (add))
(f 'd)
(add)
(if (< (length path) 5)
(c 'e)
(reverse path))))
(a b c d c e d) ;; cf. (a b c d b e d)

Doc and release update planned?

Hi, I see there is ongoing development on gauche but it hasn't seen a doc or release update since summer 2014. Do you have any plans? I'm sure some things changed :)

Importing .sld files

Gauche's (0.9.4) import doesn't recognise files with the .sld extension.

I see that it is part of the list of load suffixes here:

Gauche/src/load.c

Line 1224 in 2e21daa

SCM_APPEND1(init_load_suffixes, t, SCM_MAKE_STR(".sld")); /* R7RS library */

but import ignores that. Also, it would be good if .sld files had more precedence than .scm files (because .sld files usually contain define-library declarations that then include a .scm file of the same name containing the actual implementation).

Use glob in gauche.libutil

library-fold etc. accepts wildcard module name e.g. gauche.* but it only globs single hierarchy. We already have generic glob utility that can handle '**' wildcard. We can use it.

"ed" should not open "(standard input)" file

Just some minor annoyance.

If "ed" is called with a function defined from command line, it opens an empty "(standard input)" file. Worse, if somebody saves that file to disk, it'll open the file even if the requested function's defintion is not in there.

gosh dies if the input line is too long

I was trying to see what's wrong with profiler.scm, so I saved load-stats object and attempted to load it from gosh, the horribly long command is

(define stats '(1390234788 1390232848 1390228344 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/hashutil.scm" . 1390205860) 1390184453 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/www/cgi.scm" . 1389915249) 1389913241 1389906873 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/sxml/adaptor.scm" . 1389844755) 1389841889 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/srfi-11.scm" . 1389836318) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/sxml/tools.scm" . 1389832536) 1389829817 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/util/queue.scm" . 1389829088) 1389826947 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/text/html-lite.scm" . 1389636159) 1389634147 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/rfc/cookie.scm" . 1389521885) 1389520041 1389160036 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/srfi-14/set.scm" . 1389100652) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/rfc/mime.scm" . 1389083489) 1389081658 1389028537 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/interpolate.scm" . 1389005563) 1388815008 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/charconv.scm" . 1388808047) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/rfc/uri.scm" . 1388803904) 1388802067 1388465761 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/regexp.scm" . 1388341372) 1388339396 1388071227 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/srfi-14.scm" . 1387948293) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/text/parse.scm" . 1387945348) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/rfc/822.scm" . 1387941210) 1387939343 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/file/util.scm" . 1387902376) 1387900544 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/text/tree.scm" . 1387883765) 1387881021 1387800293 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/condutil.scm" . 1387714350) 1387682978 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/mop/propagate.scm" . 1387555823) 1387551838 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/srfi-19.scm" . 1387534780) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/control/thread-pool.scm" . 1387531688) 1387529654 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/control/job.scm" . 1387423066) 1387421157 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/vport.scm" . 1387283724) 1387281011 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/threads.scm" . 1387271625) 1387269639 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/selector.scm" . 1387198944) 1387197017 1387144168 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/srfi-0.scm" . 1387110952) 1387054111 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/fcntl.scm" . 1387049113) 1387046983 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/srfi-13.scm" . 1387036229) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/logger.scm" . 1387033407) 1387031686 1387027956 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/modutil.scm" . 1386997225) 1386984954 1386909268 1386685288 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/srfi-31.scm" . 1386683185) 1386536626 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/srfi-26.scm" . 1386530156) 1386437995 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/partcont.scm" . 1386431450) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/generator.scm" . 1386427163) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/lazy.scm" . 1386424118) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/net.scm" . 1386419246) 1386417088 1386354430 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/util/match.scm" . 1386347138) 1386345256 1386257947 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/data/queue.scm" . 1386251900) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/uvector.scm" . 1386248513) 1386246538 1386231452 1386221587 1386076884 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/common-macros.scm" . 1385971076) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/procedure.scm" . 1385966585) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/collection.scm" . 1385954513) 1385952730 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/srfi-1.scm" . 1385912710) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/sequence.scm" . 1385910120) ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/record.scm" . 1385907570) 1385905587 ("/home/pi/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/parameter.scm" . 1385893424) ("/home/pi/w/Gauche-makiki//makiki.sci" . 1385889438) ("/home/pi/w/Gauche-makiki/hello.scm" . 1385887118)))

and this is the last from gosh

READ-ERROR: Read error at "(standard input)":line 2: EOF encountered in a string literal: " . 1385887118)))\n"

It would be nice if gosh does not have this limit, but I can load this from a file for instance to work around if it's too much work.

Compile-time renaming in er-macro expansion

When er-macro is defined in toplevel within named modules, the rename procedure is simply converting symbols to global identifiers. We don't need to do it every time the macro is invoked, for the result is always identical. It can be especially effective when we're precompiling macros, for the identifiers can be emitted as constant values initialized once.

In order to do so, we have to detect particular rename procedure that can be safe to compute at compile time. The general mechanism would be this: (1) Allowing procedures to have flag to indicate it's computable at compile time, and (2) er-renamer will mark the rename procedure so if it's the case. The first mechanism would be generally useful for compile-time computation (like C++'s constexpr)

(Another hack would be to allow er-renamer to attach compiler macros to the renamers; but that's more cumbersome and error-prone than constexpr approach.)

Build error on OSX 10.10.4: unknown type name 'ulong'

gcc -DHAVE_CONFIG_H -I. -I. -I../../src -I../../src -I../../gc/include   -no-cpp-precomp  -g -O2 -no-cpp-precomp -fPIC -fno-common  -fomit-frame-pointer  -o data--queue.o -c data--queue.c
data--queue.c:2375:2: error: unknown type name 'ulong'
 ulong _25qlength(Queue* q){{
 ^
./queue.scm:92:11: error: use of undeclared identifier 'ulong'
return (((ulong )(Q_LENGTH(q))));}}
          ^
2 errors generated.
make: *** [data--queue.o] Error 1

Build succeeded & tests passed by adding "typedef unsigned long ulong;" in src/gauche.h

run-process: support splitting arguments on windows

I don't use windows. THis is just an observation. The comment about Windows before %apply-run-process was added in 535614b (further windows support - 2007-09-18). Three years later you added arg split support, but for "run" procedure in gauche.package.util, in 249d4fd (fix gauche-package on windows - 2010-11-21).

I suppose the split code is good enough to be migrated to run-process, you just forgot about run-process when you added it.

documentation about gosh -f and -p not uptodate

It looks like there are a lot more options implemented in further_options() than documented, even not counting those "for development, not for public use". gauche-ref.texi and gosh.1.in both may need updates.

As for -p, -pload is not documented in gosh.1.in and profiler_options() should print "supported profiling options are: -ptime or -pload" instead of just "..options are: -ptime"

`begin' does not control the sequence of input/output

$ gosh -V
Gauche scheme shell, version 0.9.5 [utf-8,pthreads], x86_64-pc-linux-gnu
$ gosh -r7
gosh[r7rs.user]> (begin (display 1) (display (read)))
2 ;; <== my input
12#
gosh[r7rs.user]>

I think gauche should print 1 before ask for input.

Html document generation

  • Seems texi2html is obsoleted, and makeinfo can generate html. Switch to use makeinfo for html as well.
  • Look for the way to add customized footer for each html page---putting version number in each page would reduce confusion.

define-syntax does not accept identifiers injected with synrules

Following defMyQuote syntax should define quote with specified name but Gauche's syntax-rules does not accept identifier which inserted with syntax-rules so we cannot define TEMP here.

R7RS define-syntax should accept any identifier not only symbols so I think R7RS requires support this.

(define-syntax defMyQuote
  (syntax-rules ()
    ((_ name)
     (begin
       (define-syntax TEMP
         (syntax-rules ()
           ((_ arg)
            `arg)))
       (define-syntax name
         (syntax-rules ()
           ((_ arg)
            (TEMP arg))))))))

(defMyQuote MyQuote)

(write (MyQuote symbol))(newline)
$ gosh m.scm
*** ERROR: Compile Error: symbol required, but got #<identifier user#TEMP>
"./m.scm":14:(defMyQuote MyQuote)

$ gosh -V
Gauche scheme shell, version 0.9.4 [utf-8,pthreads], i686-pc-cygwin

Test fails around number conversion

There is some test error since pull request #84

My gosh version 0.9.5_pre1 on 32 bit x86 machine makes these test error that comes from test/number.scm:

test exact (greatest-fixnum), expects 536870912 ==> ERROR: GOT 536870911
test round->exact, expects 536870912 ==> ERROR: GOT 536870911
test floor->exact, expects 536870912 ==> ERROR: GOT 536870911
test ceiling->exact, expects 536870912 ==> ERROR: GOT 536870911
test truncate->exact, expects 536870912 ==> ERROR: GOT 536870911

Above error was comes from these tests:

(test* "exact (greatest-fixnum)" (+ (greatest-fixnum) 1) (exact (inexact (greatest-fixnum))))
(test* "round->exact" (+ (greatest-fixnum) 1) (round->exact (inexact (greatest-fixnum))))
(test* "floor->exact" (+ (greatest-fixnum) 1) (floor->exact (inexact (greatest-fixnum))))
(test* "ceiling->exact" (+ (greatest-fixnum) 1) (ceiling->exact (inexact (greatest-fixnum))))
(test* "truncate->exact" (+ (greatest-fixnum) 1) (truncate->exact (inexact (greatest-fixnum))))

And here is in interactive mode:

gosh> (greatest-fixnum)
536870911 ;; == #x1fffffff
gosh> (+ (greatest-fixnum) 1)
536870912 ;; == #x20000000
gosh> (inexact (greatest-fixnum))
536870911.0
gosh> (exact (inexact (greatest-fixnum)))
536870911

I think those tests were only works on 64 bit machine, but I can't test it.

string-map fails to return an expected value when invoking a continuation captured in given procedure

Inspired by #198:

$ gosh -r7
gosh[r7rs.user]> (let ((gauche "Gauche")
      (c #f)
      (f char-downcase)
      (g! set-car!)
      (r (cons #f #f)))
  (g! r (string-map (lambda (x)
                      (if (and (char=? x #\c) (not c))
                          (call/cc (lambda (cc) (set! c cc) (f x)))
                          (f x)))
                    gauche))
  (if c
      (let ((cc c))
        (set! c #f)
        (set! f char-upcase)
        (set! g! set-cdr!)
        (cc #\X))
      r))
("gauche" . "gaucheX")
gosh[r7rs.user]> 

I think its expected value is ("gauche" . "gauXHE").

Internal define inserted by a macro is not recognized

From http://practical-scheme.net/wiliki/wiliki.cgi?Gauche%3ABugs#H-2pth75cnp87ol

(define-library (test-lib)
  (export my-define)
  (import (scheme base))
  (begin
    (define-syntax my-define
      (syntax-rules ()
        ((_ var expr)
         (begin
           (define var expr)
           var))))
    ))
そして、以下のようにこのライブラリを使うプログラムを作成します。

(import (scheme base))
(import (only (gauche base) add-load-path use print))
(add-load-path "." :relative)
(import (test-lib))
;(use test-mod)

(define (f)
  (my-define x 100)
  (+ x 1))

(print (f))
このプログラムを実行すると、以下のエラーが出ます。

*** ERROR: syntax-error: the form can appear only in the toplevel: (#<identifier
 test-lib##<identifier test-lib#define.2d13860>.2d13500> x 100)
    While compiling "./test.scm" at line 7: (define (f) (my-define x 100) (+ x 1
))
    While loading "./test.scm" at line 9

[R7RS] exporting imported identifiers from a library definition is broken

The next problem I've run into is exporting identifiers from an R7RS library definition that have been imported into it from another module. I'm wrapping some procedures/macros so that I provide a common portable interface to the rest of my codebase. One of the things I'm abstracting here are hash tables, that way I have a subset of the interface that matches the upcoming R7RS-large specification (pretty close to R6RS/SRFI 69).

Unfortunately, being able to forward identifiers via the export list seems to be broken in Gauche, whereas it works in both Chibi and Chicken Scheme implementations when running in R7RS mode. Here's how to reproduce the problem:

testlib.scm

(define-library (testlib)
  (export make-hash-table hash-table?)
  (import
    (only (gauche base) hash-table?)
    (prefix (gauche base) gauche:))
  (begin
    (define (make-hash-table)
      (gauche:make-hash-table 'equal?))))

Then I run gosh, load and import the library, and try to use the exported procedures. Here's what happens:

$ gosh -r7 -I. -ltestlib.scm
gosh[r7rs.user]> (import (testlib))
#<undef>
gosh[r7rs.user]> (define ht (make-hash-table))
ht
gosh[r7rs.user]> ht
#<hash-table equal? 0x1947780>
gosh[r7rs.user]> (hash-table? ht)
*** ERROR: unbound variable: hash-table?
Stack Trace:
_______________________________________
  0  (hash-table? ht)
        At line 4 of "(standard input)"
  1  (eval expr env)
        At line 220 of "/usr/local/share/gauche-0.9/0.9.5_pre1/lib/gauche/interactive.scm"
gosh[r7rs.user]> 

hash-table? should be bound to the hash-table? procedure imported from (gauche base) inside of (testlib).

Portable hash test fail

There is another hash test failure on my 32bit machine at current master fa21486 .
This failure dose not depend SSE optimization options like -mfpmath=sse .

Testing hash tables ===========================================================
<hash function>----------------------------------------------------------------
test portable hash (new, legacy), expects ((#f 3428989595 3428989595) (#t 64744347 64744347) (#\a 3754065427 3754065427) (#\null 3668339987 3668339987) (0 2654435761 2654435761) (1 387276917 387276917) (-1 626627309 626627309) (45174651375937459317569347657 3141754399 3238994630) (1.1 422198126 2919879337) (-1.1 1605610326 1375087959) (3.767278962604361e-10 2757400275 0) (3.767278962604362e-10 3531954109 1) (3.767278962604363e-10 11540647 1) (-3.767278962604361e-10 2026009339 0) (-3.767278962604362e-10 2800563173 4294967295) (-3.767278962604363e-10 3575117007 4294967295) (3.474701543e9 3084059771 1981271040) (3.474701544e9 3329426555 0) (-3.474701544e9 3146578821 0) (+inf.0 4190203669 0) (+nan.0 387276917 0) (1/2 1401181143 1401181143) (-5/4 91423867 91423867) (3.0+1.0i 1132007613 2027808452) (() 995466395 995466395) ((#f a 0) 835482592 509715512) (#(#t :b 3.2) 1745849782 1522869008) ("" 1937178839 0) ("zye" 2086745366 121094) (abc 1198583518 96354) (:foo 2393797652 101574)) ==> ERROR: GOT ((#f 3428989595 3428989595) (#t 64744347 64744347) (#\a 3754065427 3754065427) (#\null 3668339987 3668339987) (0 2654435761 2654435761) (1 387276917 387276917) (-1 626627309 626627309) (45174651375937459317569347657 17769158 3238994630) (1.1 324783707 2919879337) (-1.1 434454083 1375087959) (3.767278962604361e-10 524233782 0) (3.767278962604362e-10 225045792 1) (3.767278962604363e-10 462728714 1) (-3.767278962604361e-10 329713758 0) (-3.767278962604362e-10 30525768 4294967295) (-3.767278962604363e-10 268208690 4294967295) (3.474701543e9 314022366 1981271040) (3.474701544e9 22518238 0) (-3.474701544e9 376541416 0) (+inf.0 432107285 0) (+nan.0 387276917 0) (1/2 327439319 1401181143) (-5/4 91423867 91423867) (3.0+1.0i 27332797 2027808452) (() 995466395 995466395) ((#f a 0) 977371803 509715512) (#(#t :b 3.2) 2402879225 1522869008) ("" 3183946422 0) ("zye" 1276445264 121094) (abc 4121390185 96354) (:foo 2984772893 101574))

libc5 support code in os_dep.c breaks compilation with musl libc

Trying to build gauche on a linux system with musl libc (http://musl-libc.org) fails in Buildroot:

In file included from os_dep.c:44:0:
/home/peko/autobuild/instance-0/output/host/usr/arm-buildroot-linux-musleabihf/sysroot/usr/include/asm/sigcontext.h:9:8: error: redefinition of 'struct sigcontext'
 struct sigcontext {
        ^
In file included from /home/peko/autobuild/instance-0/output/host/usr/arm-buildroot-linux-musleabihf/sysroot/usr/include/signal.h:243:0,
                 from ./include/private/../gc_pthread_redirects.h:42,
                 from ./include/private/../gc.h:1443,
                 from ./include/private/gc_priv.h:46,
                 from os_dep.c:17:
/home/peko/autobuild/instance-0/output/host/usr/arm-buildroot-linux-musleabihf/sysroot/usr/include/bits/signal.h:11:16: note: originally defined here
 typedef struct sigcontext

The same issue was reported to bdwgc: ivmai/bdwgc#66 and fixed in ivmai/bdwgc@c887470.

optional arguments in cgen's define-cptr are not effective

I have a declaration like this

(define-cptr <git-repository> "git_repository*" "Git_RepositoryClass"
  "GIT_REPOP" "GIT_REPO" "GIT_REPO_VALUE"
  :print repo-print
  :cleanup repo-cleanup)

but the generated code is

Git_RepositoryClass = Scm_MakeForeignPointerClass(Scm_CurrentModule(),"<git-repository>", NULL, NULL, 0);

cleanup-proc and print-proc are not passed to that call. Adding #?= at line 1665 in cgen/stub.scm i got

#?="/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/cgen/stub.scm":1665:(assq-ref clauses 'print)
#?-    #f

make-default-console doesn't work on OS X El Capitan

On OS X 10.11.1

gosh> (gauche-version)
"0.9.5_pre1"
gosh> (sys-getenv "TERM")
"xterm-256color"
gosh> (member (sys-getenv "TERM") '("vt100" "vt102" "vt220" "xterm" "rxvt"))
#f
gosh> (make-default-console)
*** ERROR: Unsupported terminal type: xterm-256color

Better error reporting on invalid cise forms

I got this invalid define-cfn because return value needs to be wrapped in ()

(define-cfn GIT_INDEX_ENTRY_VALUE (obj) ::const git_index_entry* :static
  (return (Scm_ForeignPointerRef (SCM_FOREIGN_POINTER obj))))

and "gauche-package compile" gives me the below error message. What I need is the location of this incorrect form so I can examine and correct it. But I don't see the location is printed anywhere.It's quite hard to track down this form manually.

"/home/pclouds/opt/gauche/bin/gauche-package" compile --libs -lgit2 --cflags "-Wall -Wno-unused-label -Wno-unused-but-set-variable" \
  --local="/tmp/libgit2" --verbose libgit2 ./libgit2.c ./libgit2lib.stub
*** ERROR: Invalid CISE form:  :static
Stack Trace:
_______________________________________
  0  (map (cut render-rec <> env) (cdr form))
        At line 574 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/cgen/cise.scm"
  1  (expander form env)
        At line 350 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/cgen/cise.scm"
  2  (render-rec (expander form env) env)
        At line 350 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/cgen/cise.scm"
  3  (render-rec form env)
        At line 302 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/cgen/cise.scm"
  4  (cise-render-to-string `(begin ,@body) 'stmt)
        At line 454 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/cgen/cise.scm"
  5  (expander form env)
        At line 350 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/cgen/cise.scm"
  6  (render-rec (expander form env) env)
        At line 350 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/cgen/cise.scm"
  7  (render-rec form env)
        At line 302 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/cgen/cise.scm"
  8  (cise-render-to-string `(define-cfn ,@args) 'toplevel)
        At line 323 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/cgen/stub.scm"
  9  (cgen-stub-parse-form form)
        At line 258 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/cgen/stub.scm"
 10  (fn item r)
        At line 242 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/procedure.scm"
 11  (with-input-from-file stubfile (cut generator-fold (^ (form decl-s
        At line 252 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/cgen/stub.scm"
 12  (cgen-genstub file)
        At line 84 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/package/compile.scm"
 13  (with-error-handler (lambda (e) (exit-handler x) (h) (raise e)) (l
        [unknown location]
 14  (apply gauche-package-compile src (delete-keyword :output args))
        At line 122 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/package/compile.scm"
 15  (map (lambda (src) (cond ((equal? (path-extension src) OBJEXT) src
        At line 119 of "/home/pclouds/opt/gauche/share/gauche-0.9/0.9.5_pre1/lib/gauche/package/compile.scm"
 16  (with-error-handler (lambda (e) (let ((e e)) (%guard-rec e e (else
        [unknown location]
 17  (x (cddr args))
        [unknown location]
make: *** [libgit2.so] L?i 70

Move builtin macros into core

Now that er-macros can be precompiled, we can have builtin macros inside core (instead of in common-macros.scm etc.)

NB: We've changed the expansion of er-macro; we might want to do this after 0.9.6 so that the core macros can be compiled with the new er-macro expander (instead of 0.9.5 one).

Allow mixins for records

Records are single-inheritance, but we can safely allow mixins as far as they don't add slots.

Escape sequences for "invalid" characters

Since we added r7rs support, \x escape sequence in a string and a character literal is interpreted as unicode codepoint in r7rs compatible mode. It loses capability of writing raw octet value in the native encoding, when the native encoding is sjis or eucjp.

We can still use legacy mode to interpret \xNN as a raw octet, but for the better compatibility and read/write invariance, it might be better to introduce another escape sequence that specifically indicates raw octets. (It's especially important in incomplete string literals. Such raw octet representation allows writing portable incomplete string literal.)

Related: #185

text.console init-keyword typo

lib/text/console.scm
line 84
(reverse :init-keyword :bright :init-value #f)
→ (reverse :init-keyword :reverse :init-value #f)
line 85
(underscore :init-keyword :bright :init-value #f)))
→ (underscore :init-keyword :underscore :init-value #f)))

R7RS `import` and environment of `load`

Using Gauche from git (5ac6b1d from Jul 3)

When using R7RS import, calling load evaluates the code in a different environment that doesn't include the imported identifiers, but it works fine with Gauche's use:

a.scm:

(define-library (a)
  (import (scheme base))
  (export blah)
  (begin
    (define blah "blah")))

b.scm:

(display blah)

With Gauche's use:

gosh> (use a) 
#<undef>
gosh> (load "b")
blah#t
gosh>

With R7RS's import:

gosh[r7rs.user]> (import (scheme base) (scheme load))
#<undef>
gosh[r7rs.user]> (import (a))
#<undef>
gosh[r7rs.user]> (load "b")
*** ERROR: unbound variable: blah
    While loading "./b.scm" at line 1
Stack Trace:
_______________________________________
  0  blah

  1  (eval expr env)
        At line 254 of "/usr/local/share/gauche-0.9/0.9.5_pre1/lib/gauche/interactive.scm"

Hash function test fail

Test failed on my 32-bit Linux machine.

I think it comes from a difference of internal floating point number format between 64bit and 32 bit architecture.
Please check src/number.c:Scm_DecodeFlonum() or some other point.

Testing hash tables ===========================================================
<hash function>----------------------------------------------------------------
test portable hash, expects ((#f . 3428989595) (#t . 64744347) (#\a . 3754065427) (#\null . 3668339987) (0 . 2654435761) (1 . 387276917) (-1 . 626627309) (45174651375937459317569347657 . 3238994630) (1.1 . 2919879337) (-1.1 . 1375087959) (+inf.0 . 0) (+nan.0 . 0) (1/2 . 1401181143) (-5/4 . 91423867) (3.0+1.0i . 2027808452) (() . 995466395) ((#f a 0) . 509715512) (#(#t :b 3.2) . 1522869008) ("" . 0) ("zye" . 121094) (abc . 96354) (:foo . 101574)) ==> ERROR: GOT ((#f . 3428989595) (#t . 64744347) (#\a . 3754065427) (#\null . 3668339987) (0 . 2654435761) (1 . 387276917) (-1 . 626627309) (45174651375937459317569347657 . 3238994630) (1.1 . 2919879337) (-1.1 . 2147483648) (+inf.0 . 0) (+nan.0 . 2147483648) (1/2 . 1401181143) (-5/4 . 91423867) (3.0+1.0i . 0) (() . 995466395) ((#f a 0) . 509715512) (#(#t :b 3.2) . 1618609165) ("" . 0) ("zye" . 121094) (abc . 96354) (:foo . 101574))

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.