Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Browse files

Perlito5 - javascript: add sprintf(), printf()

  • Loading branch information...
commit 2d338cf41993eb165270cc6beac9665f862ce0d2 1 parent 2f51501
@fglock authored
View
2  ChangeLog
@@ -18,7 +18,7 @@ dev 2012-04-12
-- negative index in array
-- more file and process operations: chdir, unlink, close, exit
-- control functions: next, last, redo, break
--- more functions: rand
+-- more functions: rand, printf, sprintf
-- "continue" blocks
- perl5 backend:
View
1  TODO-perlito5
@@ -193,7 +193,6 @@ TODO list for Perlito5
-- finish "overload" implementation
-- pack(), unpack()
--- sprintf()
-- y()()
-- BEGIN{} should execute in the environment of the program under compilation
View
210 html/perlito5.js
@@ -958,7 +958,6 @@ CORE.length = function(List__) {
CORE.pack = function(List__) { CORE.warn([ "CORE::pack not implemented" ]) };
CORE.unpack = function(List__) { CORE.warn([ "CORE::unpack not implemented" ]) };
-CORE.sprintf = function(List__) { CORE.warn([ "CORE::sprintf not implemented" ]) };
CORE.ref = function(List__) {
var o = List__[0];
@@ -1134,6 +1133,213 @@ if (isNode) {
}
+/**
+ * Copyright (c) 2010 Jakob Westhoff
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+
+CORE.sprintf = function(List__) {
+ var format = List__[0];
+ var list = List__[1];
+
+ // Check for format definition
+ if ( typeof format != 'string' ) {
+ CORE.die(["sprintf: The first arguments need to be a valid format string."]);
+ }
+
+ /**
+ * Define the regex to match a formating string
+ * The regex consists of the following parts:
+ * percent sign to indicate the start
+ * (optional) sign specifier
+ * (optional) padding specifier
+ * (optional) alignment specifier
+ * (optional) width specifier
+ * (optional) precision specifier
+ * type specifier:
+ * % - literal percent sign
+ * b - binary number
+ * c - ASCII character represented by the given value
+ * d - signed decimal number
+ * f - floating point value
+ * o - octal number
+ * s - string
+ * x - hexadecimal number (lowercase characters)
+ * X - hexadecimal number (uppercase characters)
+ */
+ var r = new RegExp( /%(\+)?([0 ]|'(.))?(-)?([0-9]+)?(\.([0-9]+))?([%bcdfosxX])/g );
+
+ /**
+ * Each format string is splitted into the following parts:
+ * 0: Full format string
+ * 1: sign specifier (+)
+ * 2: padding specifier (0/<space>/'<any char>)
+ * 3: if the padding character starts with a ' this will be the real
+ * padding character
+ * 4: alignment specifier
+ * 5: width specifier
+ * 6: precision specifier including the dot
+ * 7: precision specifier without the dot
+ * 8: type specifier
+ */
+ var parts = [];
+ var paramIndex = 0;
+ while ( part = r.exec( format ) ) {
+ // Check if an input value has been provided, for the current
+ // format string
+ if ( paramIndex >= list.length ) {
+ CORE.die(["sprintf: At least one argument was missing."]);
+ }
+
+ parts[parts.length] = {
+ /* beginning of the part in the string */
+ begin: part.index,
+ /* end of the part in the string */
+ end: part.index + part[0].length,
+ /* force sign */
+ sign: ( part[1] == '+' ),
+ /* is the given data negative */
+ negative: ( parseInt( list[paramIndex] ) < 0 ) ? true : false,
+ /* padding character (default: <space>) */
+ padding: ( part[2] == undefined )
+ ? ( ' ' ) /* default */
+ : ( ( part[2].substring( 0, 1 ) == "'" )
+ ? ( part[3] ) /* use special char */
+ : ( part[2] ) /* use normal <space> or zero */
+ ),
+ /* should the output be aligned left?*/
+ alignLeft: ( part[4] == '-' ),
+ /* width specifier (number or false) */
+ width: ( part[5] != undefined ) ? part[5] : false,
+ /* precision specifier (number or false) */
+ precision: ( part[7] != undefined ) ? part[7] : false,
+ /* type specifier */
+ type: part[8],
+ /* the given data associated with this part converted to a string */
+ data: ( part[8] != '%' ) ? String ( list[paramIndex++] ) : false
+ };
+ }
+
+ var newString = "";
+ var start = 0;
+ // Generate our new formated string
+ for( var i=0; i<parts.length; ++i ) {
+ // Add first unformated string part
+ newString += format.substring( start, parts[i].begin );
+
+ // Mark the new string start
+ start = parts[i].end;
+
+ // Create the appropriate preformat substitution
+ // This substitution is only the correct type conversion. All the
+ // different options and flags haven't been applied to it at this
+ // point
+ var preSubstitution = "";
+ switch ( parts[i].type ) {
+ case '%':
+ preSubstitution = "%";
+ break;
+ case 'b':
+ preSubstitution = Math.abs( parseInt( parts[i].data ) ).toString( 2 );
+ break;
+ case 'c':
+ preSubstitution = String.fromCharCode( Math.abs( parseInt( parts[i].data ) ) );
+ break;
+ case 'd':
+ preSubstitution = String( Math.abs( parseInt( parts[i].data ) ) );
+ break;
+ case 'f':
+ preSubstitution = ( parts[i].precision == false )
+ ? ( String( ( Math.abs( parseFloat( parts[i].data ) ) ) ) )
+ : ( Math.abs( parseFloat( parts[i].data ) ).toFixed( parts[i].precision ) );
+ break;
+ case 'o':
+ preSubstitution = Math.abs( parseInt( parts[i].data ) ).toString( 8 );
+ break;
+ case 's':
+ preSubstitution = parts[i].data.substring( 0, parts[i].precision ? parts[i].precision : parts[i].data.length ); /* Cut if precision is defined */
+ break;
+ case 'x':
+ preSubstitution = Math.abs( parseInt( parts[i].data ) ).toString( 16 ).toLowerCase();
+ break;
+ case 'X':
+ preSubstitution = Math.abs( parseInt( parts[i].data ) ).toString( 16 ).toUpperCase();
+ break;
+ default:
+ throw 'sprintf: Unknown type "' + parts[i].type + '" detected. This should never happen. Maybe the regex is wrong.';
+ }
+
+ // The % character is a special type and does not need further processing
+ if ( parts[i].type == "%" ) {
+ newString += preSubstitution;
+ continue;
+ }
+
+ // Modify the preSubstitution by taking sign, padding and width
+ // into account
+
+ // Pad the string based on the given width
+ if ( parts[i].width != false ) {
+ // Padding needed?
+ if ( parts[i].width > preSubstitution.length )
+ {
+ var origLength = preSubstitution.length;
+ for( var j = 0; j < parts[i].width - origLength; ++j )
+ {
+ preSubstitution = ( parts[i].alignLeft == true )
+ ? ( preSubstitution + parts[i].padding )
+ : ( parts[i].padding + preSubstitution );
+ }
+ }
+ }
+
+ // Add a sign symbol if neccessary or enforced, but only if we are
+ // not handling a string
+ if ( parts[i].type == 'b'
+ || parts[i].type == 'd'
+ || parts[i].type == 'o'
+ || parts[i].type == 'f'
+ || parts[i].type == 'x'
+ || parts[i].type == 'X' ) {
+ if ( parts[i].negative == true ) {
+ preSubstitution = "-" + preSubstitution;
+ }
+ else if ( parts[i].sign == true ) {
+ preSubstitution = "+" + preSubstitution;
+ }
+ }
+
+ // Add the substitution to the new string
+ newString += preSubstitution;
+ }
+
+ // Add the last part of the given format string, which may still be there
+ newString += format.substring( start, format.length );
+
+ return newString;
+};
+
+CORE.printf = function(List__) {
+ return CORE.print([ CORE.sprintf(List__) ]);
+};
+
var p5want = null;
var p5100 = p5pkg['main'];
(function () {
@@ -11809,7 +12015,7 @@ return r;
p5pkg["Perlito5::Runtime"].push([p5pkg["main"]["List_INC"], [p5pkg["Perlito5::Runtime"]["v__"]]], null);
}, p5list_to_a(p5pkg["Perlito5::Runtime"].split(p5list_to_a(':', p5or(p5pkg["main"]["Hash_ENV"]['PERL5LIB'], function () { return '' })), 1)), false, "");
(p5pkg["Perlito5"]["v_SPECIAL_VAR"] = ((new p5HashRef(p5a_to_h(p5list_to_a('$_', 'ARG', '$&', '$MATCH', '$`', '$PREMATCH', '$' + String.fromCharCode(39), '$POSTMATCH', '$+', '$LAST_PAREN_MATCH', '@+', '@LAST_MATCH_END', '%+', '%LAST_PAREN_MATCH', '@-', '@LAST_MATCH_START', '$|', 'autoflush', '$/', '$RS', '@_', '@ARG', '< $', '$EUID', '$.', '$NR', '< $< ', '$UID', '$(', '$GID', '$#', null, '$@', '$EVAL_ERROR', '$=', '$FORMAT_LINES_PER_PAGE', '$,', '$OFS', '$?', '$CHILD_ERROR', '$*', null, '$[', null, '$$', '$PID', '%-', null, '$~', '$FORMAT_NAME', '$-', '$FORMAT_LINES_LEFT', '$&', '$MATCH', '$%', '$FORMAT_PAGE_NUMBER', '$)', '$EGID', '$]', null, '$!', '$ERRNO', '$;', '$SUBSEP', '$' + String.fromCharCode(92), '$ORS', '%!', null, '$"', '$LIST_SEPARATOR', '$_', '$ARG', '$:', 'FORMAT_LINE_BREAK_CHARACTERS'))))));
- (p5pkg["Perlito5"]["v_CORE_PROTO"] = ((new p5HashRef(p5a_to_h(p5list_to_a('CORE::shutdown', '*$', 'CORE::chop', null, 'CORE::lstat', '*', 'CORE::rename', '$$', 'CORE::lock', String.fromCharCode(92) + '$', 'CORE::rand', ';$', 'CORE::gmtime', ';$', 'CORE::gethostbyname', '$', 'CORE::each', String.fromCharCode(92) + '[@%]', 'CORE::ref', '_', 'CORE::syswrite', '*$;$$', 'CORE::msgctl', '$$$', 'CORE::getnetbyname', '$', 'CORE::write', ';*', 'CORE::alarm', '_', 'CORE::print', null, 'CORE::getnetent', '', 'CORE::semget', '$$$', 'CORE::use', null, 'CORE::abs', '_', 'CORE::break', '', 'CORE::undef', null, 'CORE::no', null, 'CORE::eval', null, 'CORE::split', null, 'CORE::localtime', ';$', 'CORE::sort', null, 'CORE::chown', '@', 'CORE::endpwent', '', 'CORE::getpwent', '', 'CORE::pos', null, 'CORE::lcfirst', '_', 'CORE::kill', '@', 'CORE::send', '*$$;$', 'CORE::endprotoent', '', 'CORE::semctl', '$$$$', 'CORE::waitpid', '$$', 'CORE::utime', '@', 'CORE::dbmclose', String.fromCharCode(92) + '%', 'CORE::getpwnam', '$', 'CORE::substr', '$$;$$', 'CORE::listen', '*$', 'CORE::getprotoent', '', 'CORE::shmget', '$$$', 'CORE::our', null, 'CORE::readlink', '_', 'CORE::shmwrite', '$$$$', 'CORE::times', '', 'CORE::package', null, 'CORE::map', null, 'CORE::join', '$@', 'CORE::rmdir', '_', 'CORE::shmread', '$$$$', 'CORE::uc', '_', 'CORE::bless', '$;$', 'CORE::closedir', '*', 'CORE::getppid', '', 'CORE::tie', null, 'CORE::readdir', '*', 'CORE::gethostent', '', 'CORE::getlogin', '', 'CORE::last', null, 'CORE::gethostbyaddr', '$$', 'CORE::accept', '**', 'CORE::log', '_', 'CORE::tell', ';*', 'CORE::readline', ';*', 'CORE::tied', null, 'CORE::socket', '*$$$', 'CORE::umask', ';$', 'CORE::sysread', '*' + String.fromCharCode(92) + '$$;$', 'CORE::syscall', '$@', 'CORE::quotemeta', '_', 'CORE::dump', '', 'CORE::opendir', '*$', 'CORE::untie', null, 'CORE::truncate', '$$', 'CORE::select', ';*', 'CORE::sleep', ';$', 'CORE::seek', '*$$', 'CORE::read', '*' + String.fromCharCode(92) + '$$;$', 'CORE::rewinddir', '*', 'CORE::scalar', null, 'CORE::wantarray', '', 'CORE::oct', '_', 'CORE::bind', '*$', 'CORE::stat', '*', 'CORE::sqrt', '_', 'CORE::getc', ';*', 'CORE::fileno', '*', 'CORE::getpeername', '*', 'CORE::sin', '_', 'CORE::getnetbyaddr', '$$', 'CORE::grep', null, 'CORE::setservent', '$', 'CORE::sub', null, 'CORE::shmctl', '$$$', 'CORE::study', null, 'CORE::msgrcv', '$$$$$', 'CORE::setsockopt', '*$$$', 'CORE::int', '_', 'CORE::pop', ';' + String.fromCharCode(92) + '@', 'CORE::link', '$$', 'CORE::exec', null, 'CORE::setpwent', '', 'CORE::mkdir', '_;$', 'CORE::sysseek', '*$$', 'CORE::endservent', '', 'CORE::chr', '_', 'CORE::when', null, 'CORE::getpwuid', '$', 'CORE::setprotoent', '$', 'CORE::reverse', '@', 'CORE::say', null, 'CORE::goto', null, 'CORE::getgrent', '', 'CORE::endnetent', '', 'CORE::hex', '_', 'CORE::binmode', '*;$', 'CORE::formline', '$@', 'CORE::getgrnam', '$', 'CORE::ucfirst', '_', 'CORE::chdir', ';$', 'CORE::setnetent', '$', 'CORE::splice', String.fromCharCode(92) + '@;$$@', 'CORE::unlink', '@', 'CORE::time', '', 'CORE::push', String.fromCharCode(92) + '@@', 'CORE::exit', ';$', 'CORE::endgrent', '', 'CORE::unshift', String.fromCharCode(92) + '@@', 'CORE::local', null, 'CORE::my', null, 'CORE::cos', '_', 'CORE::redo', null, 'CORE::warn', '@', 'CORE::getsockname', '*', 'CORE::pipe', '**', 'CORE::sprintf', '$@', 'CORE::open', '*;$@', 'CORE::setpgrp', ';$$', 'CORE::exp', '_', 'CORE::seekdir', '*$', 'CORE::getservbyport', '$$', 'CORE::given', null, 'CORE::pack', '$@', 'CORE::msgget', '$$', 'CORE::rindex', '$$;$', 'CORE::srand', ';$', 'CORE::telldir', '*', 'CORE::connect', '*$', 'CORE::getprotobyname', '$', 'CORE::msgsnd', '$$$', 'CORE::length', '_', 'CORE::state', null, 'CORE::die', '@', 'CORE::delete', null, 'CORE::getservent', '', 'CORE::getservbyname', '$$', 'CORE::setpriority', '$$$', 'CORE::lc', '_', 'CORE::fcntl', '*$$', 'CORE::chroot', '_', 'CORE::recv', '*' + String.fromCharCode(92) + '$$$', 'CORE::dbmopen', String.fromCharCode(92) + '%$$', 'CORE::socketpair', '**$$$', 'CORE::vec', '$$$', 'CORE::system', null, 'CORE::defined', '_', 'CORE::index', '$$;$', 'CORE::caller', ';$', 'CORE::close', ';*', 'CORE::atan2', '$$', 'CORE::semop', '$$', 'CORE::unpack', '$;$', 'CORE::ord', '_', 'CORE::chmod', '@', 'CORE::prototype', null, 'CORE::getprotobynumber', '$', 'CORE::values', String.fromCharCode(92) + '[@%]', 'CORE::chomp', null, 'CORE::ioctl', '*$$', 'CORE::eof', ';*', 'CORE::crypt', '$$', 'CORE::do', null, 'CORE::flock', '*$', 'CORE::wait', '', 'CORE::sethostent', '$', 'CORE::return', null, 'CORE::getsockopt', '*$$', 'CORE::fork', '', 'CORE::require', null, 'CORE::format', null, 'CORE::readpipe', '_', 'CORE::endhostent', '', 'CORE::getpgrp', ';$', 'CORE::setgrent', '', 'CORE::keys', String.fromCharCode(92) + '[@%]', 'CORE::glob', null, 'CORE::getpriority', '$$', 'CORE::reset', ';$', 'CORE::sysopen', '*$$;$', 'CORE::continue', '', 'CORE::next', null, 'CORE::getgrgid', '$', 'CORE::default', null, 'CORE::shift', ';' + String.fromCharCode(92) + '@', 'CORE::symlink', '$$', 'CORE::exists', '$', 'CORE::printf', null))))));
+ (p5pkg["Perlito5"]["v_CORE_PROTO"] = ((new p5HashRef(p5a_to_h(p5list_to_a('CORE::shutdown', '*$', 'CORE::chop', null, 'CORE::lstat', '*', 'CORE::rename', '$$', 'CORE::lock', String.fromCharCode(92) + '$', 'CORE::rand', ';$', 'CORE::gmtime', ';$', 'CORE::gethostbyname', '$', 'CORE::each', String.fromCharCode(92) + '[@%]', 'CORE::ref', '_', 'CORE::syswrite', '*$;$$', 'CORE::msgctl', '$$$', 'CORE::getnetbyname', '$', 'CORE::write', ';*', 'CORE::alarm', '_', 'CORE::print', null, 'CORE::getnetent', '', 'CORE::semget', '$$$', 'CORE::use', null, 'CORE::abs', '_', 'CORE::break', '', 'CORE::undef', null, 'CORE::no', null, 'CORE::eval', null, 'CORE::split', null, 'CORE::localtime', ';$', 'CORE::sort', null, 'CORE::chown', '@', 'CORE::endpwent', '', 'CORE::getpwent', '', 'CORE::pos', null, 'CORE::lcfirst', '_', 'CORE::kill', '@', 'CORE::send', '*$$;$', 'CORE::endprotoent', '', 'CORE::semctl', '$$$$', 'CORE::waitpid', '$$', 'CORE::utime', '@', 'CORE::dbmclose', String.fromCharCode(92) + '%', 'CORE::getpwnam', '$', 'CORE::substr', '$$;$$', 'CORE::listen', '*$', 'CORE::getprotoent', '', 'CORE::shmget', '$$$', 'CORE::our', null, 'CORE::readlink', '_', 'CORE::shmwrite', '$$$$', 'CORE::times', '', 'CORE::package', null, 'CORE::map', null, 'CORE::join', '$@', 'CORE::rmdir', '_', 'CORE::shmread', '$$$$', 'CORE::uc', '_', 'CORE::bless', '$;$', 'CORE::closedir', '*', 'CORE::getppid', '', 'CORE::tie', null, 'CORE::readdir', '*', 'CORE::gethostent', '', 'CORE::getlogin', '', 'CORE::last', null, 'CORE::gethostbyaddr', '$$', 'CORE::accept', '**', 'CORE::log', '_', 'CORE::tell', ';*', 'CORE::readline', ';*', 'CORE::tied', null, 'CORE::socket', '*$$$', 'CORE::umask', ';$', 'CORE::sysread', '*' + String.fromCharCode(92) + '$$;$', 'CORE::syscall', '$@', 'CORE::quotemeta', '_', 'CORE::dump', '', 'CORE::opendir', '*$', 'CORE::untie', null, 'CORE::truncate', '$$', 'CORE::select', ';*', 'CORE::sleep', ';$', 'CORE::seek', '*$$', 'CORE::read', '*' + String.fromCharCode(92) + '$$;$', 'CORE::rewinddir', '*', 'CORE::scalar', null, 'CORE::wantarray', '', 'CORE::oct', '_', 'CORE::bind', '*$', 'CORE::stat', '*', 'CORE::sqrt', '_', 'CORE::getc', ';*', 'CORE::fileno', '*', 'CORE::getpeername', '*', 'CORE::sin', '_', 'CORE::getnetbyaddr', '$$', 'CORE::grep', null, 'CORE::setservent', '$', 'CORE::sub', null, 'CORE::shmctl', '$$$', 'CORE::study', null, 'CORE::msgrcv', '$$$$$', 'CORE::setsockopt', '*$$$', 'CORE::int', '_', 'CORE::pop', ';' + String.fromCharCode(92) + '@', 'CORE::link', '$$', 'CORE::exec', null, 'CORE::setpwent', '', 'CORE::mkdir', '_;$', 'CORE::sysseek', '*$$', 'CORE::endservent', '', 'CORE::chr', '_', 'CORE::when', null, 'CORE::getpwuid', '$', 'CORE::setprotoent', '$', 'CORE::reverse', '@', 'CORE::say', null, 'CORE::goto', null, 'CORE::getgrent', '', 'CORE::endnetent', '', 'CORE::hex', '_', 'CORE::binmode', '*;$', 'CORE::formline', '$@', 'CORE::getgrnam', '$', 'CORE::ucfirst', '_', 'CORE::chdir', ';$', 'CORE::setnetent', '$', 'CORE::splice', String.fromCharCode(92) + '@;$$@', 'CORE::unlink', '@', 'CORE::time', '', 'CORE::push', String.fromCharCode(92) + '@@', 'CORE::exit', ';$', 'CORE::endgrent', '', 'CORE::unshift', String.fromCharCode(92) + '@@', 'CORE::local', null, 'CORE::my', null, 'CORE::cos', '_', 'CORE::redo', null, 'CORE::warn', '@', 'CORE::getsockname', '*', 'CORE::pipe', '**', 'CORE::sprintf', '$@', 'CORE::open', '*;$@', 'CORE::setpgrp', ';$$', 'CORE::exp', '_', 'CORE::seekdir', '*$', 'CORE::getservbyport', '$$', 'CORE::given', null, 'CORE::pack', '$@', 'CORE::msgget', '$$', 'CORE::rindex', '$$;$', 'CORE::srand', ';$', 'CORE::telldir', '*', 'CORE::connect', '*$', 'CORE::getprotobyname', '$', 'CORE::msgsnd', '$$$', 'CORE::length', '_', 'CORE::state', null, 'CORE::die', '@', 'CORE::delete', null, 'CORE::getservent', '', 'CORE::getservbyname', '$$', 'CORE::setpriority', '$$$', 'CORE::lc', '_', 'CORE::fcntl', '*$$', 'CORE::chroot', '_', 'CORE::recv', '*' + String.fromCharCode(92) + '$$$', 'CORE::dbmopen', String.fromCharCode(92) + '%$$', 'CORE::socketpair', '**$$$', 'CORE::vec', '$$$', 'CORE::system', null, 'CORE::defined', '_', 'CORE::index', '$$;$', 'CORE::caller', ';$', 'CORE::close', ';*', 'CORE::atan2', '$$', 'CORE::semop', '$$', 'CORE::unpack', '$;$', 'CORE::ord', '_', 'CORE::chmod', '@', 'CORE::prototype', null, 'CORE::getprotobynumber', '$', 'CORE::values', String.fromCharCode(92) + '[@%]', 'CORE::chomp', null, 'CORE::ioctl', '*$$', 'CORE::eof', ';*', 'CORE::crypt', '$$', 'CORE::do', null, 'CORE::flock', '*$', 'CORE::wait', '', 'CORE::sethostent', '$', 'CORE::return', null, 'CORE::getsockopt', '*$$', 'CORE::fork', '', 'CORE::require', null, 'CORE::format', null, 'CORE::readpipe', '_', 'CORE::endhostent', '', 'CORE::getpgrp', ';$', 'CORE::setgrent', '', 'CORE::keys', String.fromCharCode(92) + '[@%]', 'CORE::glob', null, 'CORE::getpriority', '$$', 'CORE::reset', ';$', 'CORE::sysopen', '*$$;$', 'CORE::continue', '', 'CORE::next', null, 'CORE::getgrgid', '$', 'CORE::default', null, 'CORE::shift', ';' + String.fromCharCode(92) + '@', 'CORE::symlink', '$$', 'CORE::exists', '$', 'CORE::printf', '$@'))))));
1;
})()
;
View
19 perlito5.pl
@@ -9145,7 +9145,7 @@ package main;
undef();
package Perlito5::Javascript::CORE;
sub Perlito5::Javascript::CORE::emit_javascript {
- return ((('//' . chr(10) . '//' . chr(10) . '// lib/Perlito5/Javascript/CORE.js' . chr(10) . '//' . chr(10) . '// CORE functions for "Perlito" Perl5-in-Javascript' . chr(10) . '//' . chr(10) . '// AUTHORS' . chr(10) . '//' . chr(10) . '// Flavio Soibelmann Glock fglock@gmail.com' . chr(10) . '//' . chr(10) . '// COPYRIGHT' . chr(10) . '//' . chr(10) . '// Copyright 2009, 2010, 2011, 2012 by Flavio Soibelmann Glock and others.' . chr(10) . '//' . chr(10) . '// This program is free software; you can redistribute it and/or modify it' . chr(10) . '// under the same terms as Perl itself.' . chr(10) . '//' . chr(10) . '// See http://www.perl.com/perl/misc/Artistic.html' . chr(10) . chr(10) . 'var CORE = p5pkg.CORE;' . chr(10) . chr(10) . 'var isNode = typeof require != "undefined";' . chr(10) . 'if (isNode) {' . chr(10) . ' CORE.print = function(List__) {' . chr(10) . ' var i;' . chr(10) . ' for (i = 0; i < List__.length; i++) {' . chr(10) . ' process.stdout.write(p5str(List__[i]));' . chr(10) . ' }' . chr(10) . ' return 1;' . chr(10) . ' }' . chr(10) . '} else {' . chr(10) . ' CORE.print = function(List__) {' . chr(10) . ' var i;' . chr(10) . ' for (i = 0; i < List__.length; i++) {' . chr(10) . ' write(p5str(List__[i]));' . chr(10) . ' }' . chr(10) . ' return 1;' . chr(10) . ' };' . chr(10) . '}' . chr(10) . chr(10) . 'CORE.say = function(List__) {' . chr(10) . ' CORE.print(List__);' . chr(10) . ' return CORE.print(["' . chr(92) . 'n"]);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.die = function(List__) {' . chr(10) . ' var i;' . chr(10) . ' var s = "";' . chr(10) . ' for (i = 0; i < List__.length; i++) {' . chr(10) . ' s = s + p5str(List__[i]);' . chr(10) . ' }' . chr(10) . ' p5pkg["main"]["v_@"] = "Died: " + s;' . chr(10) . ' throw(new p5_error("die", "Died: " + s));' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.warn = function(List__) {' . chr(10) . ' var i;' . chr(10) . ' var s = "";' . chr(10) . ' for (i = 0; i < List__.length; i++) {' . chr(10) . ' s = s + p5str(List__[i]);' . chr(10) . ' }' . chr(10) . ' CORE.print(["Warning: " + s + "' . chr(92) . 'n"]);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.bless = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' var pkg_name = List__[1];' . chr(10) . ' if (typeof pkg_name === "object") {' . chr(10) . ' // bless {}, Class' . chr(10) . ' o._class_ = pkg_name;' . chr(10) . ' return o;' . chr(10) . ' }' . chr(10) . ' if (!p5pkg.hasOwnProperty(pkg_name)) {' . chr(10) . ' p5make_package(pkg_name);' . chr(10) . ' }' . chr(10) . ' o._class_ = p5pkg[pkg_name];' . chr(10) . ' return o;' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.chr = function(List__) {' . chr(10) . ' var v = p5num(List__[0]);' . chr(10) . ' return String.fromCharCode(v >= 0 ? v : 65533);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.ord = function(List__) {' . chr(10) . ' return p5str(List__[0]).charCodeAt(0);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.oct = function(List__) {' . chr(10) . ' var v = List__[0];' . chr(10) . ' var b = v.substr(0,2);' . chr(10) . ' v = v.replace("_", "");' . chr(10) . ' if (b == "0b" || b == "0B") { return parseInt(v.substr(2), 2) }' . chr(10) . ' if (b == "0x" || b == "0X") { return parseInt(v.substr(2), 16) }' . chr(10) . ' return parseInt(v, 8);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.abs = function(List__) { return Math.abs(List__[0]) };' . chr(10) . 'CORE.exp = function(List__) { return Math.exp(List__[0]) };' . chr(10) . 'CORE.log = function(List__) { return Math.log(List__[0]) };' . chr(10) . 'CORE.cos = function(List__) { return Math.cos(List__[0]) };' . chr(10) . 'CORE.sin = function(List__) { return Math.sin(List__[0]) };' . chr(10) . 'CORE.sqrt = function(List__) { return Math.sqrt(List__[0]) };' . chr(10) . 'CORE.atan2 = function(List__) { return Math.atan2(List__[0], List__[1]) };' . chr(10) . 'CORE.int = function(List__) { return List__[0] > 0 ? Math.floor(List__[0]) : Math.ceil(List__[0]) };' . chr(10) . chr(10) . 'CORE.rand = function(List__) {' . chr(10) . ' var v = p5num(List__[0]) || 1;' . chr(10) . ' return Math.random() * v;' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.lc = function(List__) { return p5str(List__[0]).toLowerCase() };' . chr(10) . 'CORE.uc = function(List__) { return p5str(List__[0]).toUpperCase() };' . chr(10) . chr(10) . 'CORE.lcfirst = function(List__) {' . chr(10) . ' var s = p5str(List__[0]);' . chr(10) . ' var c = s.length > 0 ? s.slice(0,1).toLowerCase() : "";' . chr(10) . ' s = s.length > 1 ? s.substr(1) : "";' . chr(10) . ' return c + s' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.ucfirst = function(List__) {' . chr(10) . ' var s = p5str(List__[0]);' . chr(10) . ' var c = s.length > 0 ? s.slice(0,1).toUpperCase() : "";' . chr(10) . ' s = s.length > 1 ? s.substr(1) : "";' . chr(10) . ' return c + s' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.quotemeta = function(List__) {' . chr(10) . ' var s = p5str(List__[0]);' . chr(10) . ' var out = [];' . chr(10) . ' for(var i = 0; i < s.length; i++) {' . chr(10) . ' if (s.substr(i, 1).match(/[^0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ_abcdefghijklmnopqrstuvwxyz]/)) {' . chr(10) . ' out.push(String.fromCharCode(92));' . chr(10) . ' }' . chr(10) . ' out.push(s.substr(i, 1));' . chr(10) . ' }' . chr(10) . ' return out.join(""); ' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.substr = function(List__) {' . chr(10) . ' var expr = List__[0];' . chr(10) . ' var offset = List__[1];' . chr(10) . ' var length = List__[2];' . chr(10) . ' var replacement = List__[3];' . chr(10) . ' if (length < 0) {' . chr(10) . ' var s = p5str(expr);' . chr(10) . ' length = s.length - offset + length;' . chr(10) . ' } ' . chr(10) . ' return p5str(expr).substr(offset, length);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.values = function(List__, p5want) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' delete o["_each_"];' . chr(10) . ' if (p5want) {' . chr(10) . ' if (o == null) {' . chr(10) . ' return [];' . chr(10) . ' };' . chr(10) . ' if (typeof o.values === "function") {' . chr(10) . ' return o.values();' . chr(10) . ' }' . chr(10) . ' var out = [];' . chr(10) . ' for (var i in o) {' . chr(10) . ' out.push(o[i]);' . chr(10) . ' }' . chr(10) . ' return out;' . chr(10) . ' }' . chr(10) . ' return CORE.keys(List__, p5want);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.keys = function(List__, p5want) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' delete o["_each_"];' . chr(10) . ' if (p5want) {' . chr(10) . ' if (o == null) {' . chr(10) . ' return [];' . chr(10) . ' }' . chr(10) . ' if (typeof o.keys === "function") {' . chr(10) . ' return o.keys();' . chr(10) . ' }' . chr(10) . ' var out = [];' . chr(10) . ' for (var i in o) {' . chr(10) . ' out.push(i);' . chr(10) . ' }' . chr(10) . ' return out;' . chr(10) . ' }' . chr(10) . ' else {' . chr(10) . ' if (o == null) {' . chr(10) . ' return 0;' . chr(10) . ' }' . chr(10) . ' if (typeof o.keys === "function") {' . chr(10) . ' return CORE.scalar([o.keys()]);' . chr(10) . ' }' . chr(10) . ' var out = 0;' . chr(10) . ' for (var i in o) {' . chr(10) . ' out++;' . chr(10) . ' }' . chr(10) . ' return out;' . chr(10) . ' }' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.each = function(List__, p5want) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' if (o.hasOwnProperty("_each_")) {' . chr(10) . ' return o._each_(p5want)' . chr(10) . ' }' . chr(10) . ' var keys = CORE.keys([o], 1);' . chr(10) . ' var i = 0;' . chr(10) . ' o._each_ = function () {' . chr(10) . ' if (i < keys.length) {' . chr(10) . ' i++;' . chr(10) . ' return p5want ? [keys[i-1], o[keys[i-1]]] : keys[i-1];' . chr(10) . ' }' . chr(10) . ' i = 0;' . chr(10) . ' return p5want ? [] : null;' . chr(10) . ' };' . chr(10) . ' return o._each_(p5want);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.reverse = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' if (o == null) {' . chr(10) . ' return "";' . chr(10) . ' }' . chr(10) . ' if (typeof o === "string") {' . chr(10) . ' return o.split("").reverse().join("")' . chr(10) . ' }' . chr(10) . ' var out = [];' . chr(10) . ' for(var i = 0; i < o.length; i++) {' . chr(10) . ' out.unshift(o[i]);' . chr(10) . ' }' . chr(10) . ' return out;' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.splice = function(List__, p5want) {' . chr(10) . ' var array = List__.shift();' . chr(10) . ' // CORE.say([ array ]);' . chr(10) . ' var offset = p5num(List__.shift());' . chr(10) . ' var limit = List__.length ? p5num(List__.shift()) : (array.length + 1);' . chr(10) . chr(10) . ' if (limit < 0) {' . chr(10) . ' limit = array.length + limit - 1;' . chr(10) . ' }' . chr(10) . chr(10) . ' var list = [offset, limit];' . chr(10) . ' for(var i = 0; i < List__.length; i++) {' . chr(10) . ' list = p5list_to_a( list, List__[i]);' . chr(10) . ' }' . chr(10) . chr(10) . ' out = array.splice.apply(array, list);' . chr(10) . ' // CORE.say([ CORE.join([":",array]), " ofs=", offset, " lim=", limit, " list=", list, " out=", CORE.join([":",out]) ]);' . chr(10) . ' return p5want ? out : out.pop();' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.pop = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' if (o.length == null) {' . chr(10) . ' return null;' . chr(10) . ' }' . chr(10) . ' return o.pop();' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.shift = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' if (o.length == null) {' . chr(10) . ' return null;' . chr(10) . ' }' . chr(10) . ' return o.shift();' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.push = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' var v = List__[1];' . chr(10) . ' for(var i = 0; i < v.length; i++) {' . chr(10) . ' o.push(v[i]);' . chr(10) . ' }' . chr(10) . ' return o.length;' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.unshift = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' var v = List__[1];' . chr(10) . ' for(var i = v.length-1; i >= 0; i--) {' . chr(10) . ' o.unshift(v[i]);' . chr(10) . ' }' . chr(10) . ' return o.length;' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.join = function(List__) {' . chr(10) . ' var s = List__[0];' . chr(10) . ' var o = List__[1];' . chr(10) . ' return o.join(s);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.index = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' var s = List__[1];' . chr(10) . ' try {' . chr(10) . ' return o.indexOf(s, p5num(List__[2]));' . chr(10) . ' }' . chr(10) . ' catch(err) {' . chr(10) . ' return -1;' . chr(10) . ' }' . chr(10) . '};' . chr(10) . 'CORE.rindex = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' var s = List__[1];' . chr(10) . ' try {' . chr(10) . ' if (List__.length > 2) {' . chr(10) . ' var i = p5num(List__[2]);' . chr(10) . ' if (i < 0) {' . chr(10) . ' if (s.length == 0) {' . chr(10) . ' return 0;' . chr(10) . ' }' . chr(10) . ' return -1;' . chr(10) . ' }' . chr(10) . ' return o.lastIndexOf(s, i);' . chr(10) . ' }' . chr(10) . ' return o.lastIndexOf(s);' . chr(10) . ' }' . chr(10) . ' catch(err) {' . chr(10) . ' return -1;' . chr(10) . ' }' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.length = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' if (typeof o.string === "function") {' . chr(10) . ' return o.string().length;' . chr(10) . ' }' . chr(10) . ' return o.length;' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.pack = function(List__) { CORE.warn([ "CORE::pack not implemented" ]) };' . chr(10) . 'CORE.unpack = function(List__) { CORE.warn([ "CORE::unpack not implemented" ]) };' . chr(10) . 'CORE.sprintf = function(List__) { CORE.warn([ "CORE::sprintf not implemented" ]) };' . chr(10) . chr(10) . 'CORE.ref = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' if (o == null) {' . chr(10) . ' return "";' . chr(10) . ' }' . chr(10) . ' if (o._class_ && typeof o._class_._ref_ === "string") {' . chr(10) . ' // blessed reference' . chr(10) . ' return o._class_._ref_;' . chr(10) . ' }' . chr(10) . ' if (typeof o._ref_ === "string") {' . chr(10) . ' // un-blessed reference' . chr(10) . ' return o._ref_;' . chr(10) . ' }' . chr(10) . ' if (typeof o === "function") {' . chr(10) . ' return "CODE";' . chr(10) . ' }' . chr(10) . ' return "";' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.split = function(List__) {' . chr(10) . ' var pattern = List__[0];' . chr(10) . ' var s = List__[1];' . chr(10) . ' var limit = List__[2];' . chr(10) . ' if (typeof pattern === "string") {' . chr(10) . ' if (pattern == " ") {' . chr(10) . ' var res = [];' . chr(10) . ' for (var i_ = 0, a_ = s.split(/(?: |' . chr(92) . 'n)+/); i_ < a_.length ; i_++) {' . chr(10) . ' if (a_[i_] != "") {' . chr(10) . ' res.push(a_[i_])' . chr(10) . ' }' . chr(10) . ' }' . chr(10) . ' return res;' . chr(10) . ' }' . chr(10) . ' return s.split(pattern);' . chr(10) . ' }' . chr(10) . ' CORE.die(["not implemented"]);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.prototype = function(List__, data) {' . chr(10) . ' var name = List__[0];' . chr(10) . ' // TODO - fully qualify "name" using information from "data"' . chr(10) . ' // XXX - lookup in CORE::GLOBAL?' . chr(10) . ' p5pkg["Perlito5"].v_PROTO._hash_[name] || p5pkg["Perlito5"].v_CORE_PROTO._hash_[name]' . chr(10) . '};' . chr(10) . chr(10))))
+ return ((('//' . chr(10) . '//' . chr(10) . '// lib/Perlito5/Javascript/CORE.js' . chr(10) . '//' . chr(10) . '// CORE functions for "Perlito" Perl5-in-Javascript' . chr(10) . '//' . chr(10) . '// AUTHORS' . chr(10) . '//' . chr(10) . '// Flavio Soibelmann Glock fglock@gmail.com' . chr(10) . '//' . chr(10) . '// COPYRIGHT' . chr(10) . '//' . chr(10) . '// Copyright 2009, 2010, 2011, 2012 by Flavio Soibelmann Glock and others.' . chr(10) . '//' . chr(10) . '// This program is free software; you can redistribute it and/or modify it' . chr(10) . '// under the same terms as Perl itself.' . chr(10) . '//' . chr(10) . '// See http://www.perl.com/perl/misc/Artistic.html' . chr(10) . chr(10) . 'var CORE = p5pkg.CORE;' . chr(10) . chr(10) . 'var isNode = typeof require != "undefined";' . chr(10) . 'if (isNode) {' . chr(10) . ' CORE.print = function(List__) {' . chr(10) . ' var i;' . chr(10) . ' for (i = 0; i < List__.length; i++) {' . chr(10) . ' process.stdout.write(p5str(List__[i]));' . chr(10) . ' }' . chr(10) . ' return 1;' . chr(10) . ' }' . chr(10) . '} else {' . chr(10) . ' CORE.print = function(List__) {' . chr(10) . ' var i;' . chr(10) . ' for (i = 0; i < List__.length; i++) {' . chr(10) . ' write(p5str(List__[i]));' . chr(10) . ' }' . chr(10) . ' return 1;' . chr(10) . ' };' . chr(10) . '}' . chr(10) . chr(10) . 'CORE.say = function(List__) {' . chr(10) . ' CORE.print(List__);' . chr(10) . ' return CORE.print(["' . chr(92) . 'n"]);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.die = function(List__) {' . chr(10) . ' var i;' . chr(10) . ' var s = "";' . chr(10) . ' for (i = 0; i < List__.length; i++) {' . chr(10) . ' s = s + p5str(List__[i]);' . chr(10) . ' }' . chr(10) . ' p5pkg["main"]["v_@"] = "Died: " + s;' . chr(10) . ' throw(new p5_error("die", "Died: " + s));' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.warn = function(List__) {' . chr(10) . ' var i;' . chr(10) . ' var s = "";' . chr(10) . ' for (i = 0; i < List__.length; i++) {' . chr(10) . ' s = s + p5str(List__[i]);' . chr(10) . ' }' . chr(10) . ' CORE.print(["Warning: " + s + "' . chr(92) . 'n"]);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.bless = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' var pkg_name = List__[1];' . chr(10) . ' if (typeof pkg_name === "object") {' . chr(10) . ' // bless {}, Class' . chr(10) . ' o._class_ = pkg_name;' . chr(10) . ' return o;' . chr(10) . ' }' . chr(10) . ' if (!p5pkg.hasOwnProperty(pkg_name)) {' . chr(10) . ' p5make_package(pkg_name);' . chr(10) . ' }' . chr(10) . ' o._class_ = p5pkg[pkg_name];' . chr(10) . ' return o;' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.chr = function(List__) {' . chr(10) . ' var v = p5num(List__[0]);' . chr(10) . ' return String.fromCharCode(v >= 0 ? v : 65533);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.ord = function(List__) {' . chr(10) . ' return p5str(List__[0]).charCodeAt(0);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.oct = function(List__) {' . chr(10) . ' var v = List__[0];' . chr(10) . ' var b = v.substr(0,2);' . chr(10) . ' v = v.replace("_", "");' . chr(10) . ' if (b == "0b" || b == "0B") { return parseInt(v.substr(2), 2) }' . chr(10) . ' if (b == "0x" || b == "0X") { return parseInt(v.substr(2), 16) }' . chr(10) . ' return parseInt(v, 8);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.abs = function(List__) { return Math.abs(List__[0]) };' . chr(10) . 'CORE.exp = function(List__) { return Math.exp(List__[0]) };' . chr(10) . 'CORE.log = function(List__) { return Math.log(List__[0]) };' . chr(10) . 'CORE.cos = function(List__) { return Math.cos(List__[0]) };' . chr(10) . 'CORE.sin = function(List__) { return Math.sin(List__[0]) };' . chr(10) . 'CORE.sqrt = function(List__) { return Math.sqrt(List__[0]) };' . chr(10) . 'CORE.atan2 = function(List__) { return Math.atan2(List__[0], List__[1]) };' . chr(10) . 'CORE.int = function(List__) { return List__[0] > 0 ? Math.floor(List__[0]) : Math.ceil(List__[0]) };' . chr(10) . chr(10) . 'CORE.rand = function(List__) {' . chr(10) . ' var v = p5num(List__[0]) || 1;' . chr(10) . ' return Math.random() * v;' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.lc = function(List__) { return p5str(List__[0]).toLowerCase() };' . chr(10) . 'CORE.uc = function(List__) { return p5str(List__[0]).toUpperCase() };' . chr(10) . chr(10) . 'CORE.lcfirst = function(List__) {' . chr(10) . ' var s = p5str(List__[0]);' . chr(10) . ' var c = s.length > 0 ? s.slice(0,1).toLowerCase() : "";' . chr(10) . ' s = s.length > 1 ? s.substr(1) : "";' . chr(10) . ' return c + s' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.ucfirst = function(List__) {' . chr(10) . ' var s = p5str(List__[0]);' . chr(10) . ' var c = s.length > 0 ? s.slice(0,1).toUpperCase() : "";' . chr(10) . ' s = s.length > 1 ? s.substr(1) : "";' . chr(10) . ' return c + s' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.quotemeta = function(List__) {' . chr(10) . ' var s = p5str(List__[0]);' . chr(10) . ' var out = [];' . chr(10) . ' for(var i = 0; i < s.length; i++) {' . chr(10) . ' if (s.substr(i, 1).match(/[^0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ_abcdefghijklmnopqrstuvwxyz]/)) {' . chr(10) . ' out.push(String.fromCharCode(92));' . chr(10) . ' }' . chr(10) . ' out.push(s.substr(i, 1));' . chr(10) . ' }' . chr(10) . ' return out.join(""); ' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.substr = function(List__) {' . chr(10) . ' var expr = List__[0];' . chr(10) . ' var offset = List__[1];' . chr(10) . ' var length = List__[2];' . chr(10) . ' var replacement = List__[3];' . chr(10) . ' if (length < 0) {' . chr(10) . ' var s = p5str(expr);' . chr(10) . ' length = s.length - offset + length;' . chr(10) . ' } ' . chr(10) . ' return p5str(expr).substr(offset, length);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.values = function(List__, p5want) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' delete o["_each_"];' . chr(10) . ' if (p5want) {' . chr(10) . ' if (o == null) {' . chr(10) . ' return [];' . chr(10) . ' };' . chr(10) . ' if (typeof o.values === "function") {' . chr(10) . ' return o.values();' . chr(10) . ' }' . chr(10) . ' var out = [];' . chr(10) . ' for (var i in o) {' . chr(10) . ' out.push(o[i]);' . chr(10) . ' }' . chr(10) . ' return out;' . chr(10) . ' }' . chr(10) . ' return CORE.keys(List__, p5want);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.keys = function(List__, p5want) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' delete o["_each_"];' . chr(10) . ' if (p5want) {' . chr(10) . ' if (o == null) {' . chr(10) . ' return [];' . chr(10) . ' }' . chr(10) . ' if (typeof o.keys === "function") {' . chr(10) . ' return o.keys();' . chr(10) . ' }' . chr(10) . ' var out = [];' . chr(10) . ' for (var i in o) {' . chr(10) . ' out.push(i);' . chr(10) . ' }' . chr(10) . ' return out;' . chr(10) . ' }' . chr(10) . ' else {' . chr(10) . ' if (o == null) {' . chr(10) . ' return 0;' . chr(10) . ' }' . chr(10) . ' if (typeof o.keys === "function") {' . chr(10) . ' return CORE.scalar([o.keys()]);' . chr(10) . ' }' . chr(10) . ' var out = 0;' . chr(10) . ' for (var i in o) {' . chr(10) . ' out++;' . chr(10) . ' }' . chr(10) . ' return out;' . chr(10) . ' }' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.each = function(List__, p5want) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' if (o.hasOwnProperty("_each_")) {' . chr(10) . ' return o._each_(p5want)' . chr(10) . ' }' . chr(10) . ' var keys = CORE.keys([o], 1);' . chr(10) . ' var i = 0;' . chr(10) . ' o._each_ = function () {' . chr(10) . ' if (i < keys.length) {' . chr(10) . ' i++;' . chr(10) . ' return p5want ? [keys[i-1], o[keys[i-1]]] : keys[i-1];' . chr(10) . ' }' . chr(10) . ' i = 0;' . chr(10) . ' return p5want ? [] : null;' . chr(10) . ' };' . chr(10) . ' return o._each_(p5want);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.reverse = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' if (o == null) {' . chr(10) . ' return "";' . chr(10) . ' }' . chr(10) . ' if (typeof o === "string") {' . chr(10) . ' return o.split("").reverse().join("")' . chr(10) . ' }' . chr(10) . ' var out = [];' . chr(10) . ' for(var i = 0; i < o.length; i++) {' . chr(10) . ' out.unshift(o[i]);' . chr(10) . ' }' . chr(10) . ' return out;' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.splice = function(List__, p5want) {' . chr(10) . ' var array = List__.shift();' . chr(10) . ' // CORE.say([ array ]);' . chr(10) . ' var offset = p5num(List__.shift());' . chr(10) . ' var limit = List__.length ? p5num(List__.shift()) : (array.length + 1);' . chr(10) . chr(10) . ' if (limit < 0) {' . chr(10) . ' limit = array.length + limit - 1;' . chr(10) . ' }' . chr(10) . chr(10) . ' var list = [offset, limit];' . chr(10) . ' for(var i = 0; i < List__.length; i++) {' . chr(10) . ' list = p5list_to_a( list, List__[i]);' . chr(10) . ' }' . chr(10) . chr(10) . ' out = array.splice.apply(array, list);' . chr(10) . ' // CORE.say([ CORE.join([":",array]), " ofs=", offset, " lim=", limit, " list=", list, " out=", CORE.join([":",out]) ]);' . chr(10) . ' return p5want ? out : out.pop();' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.pop = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' if (o.length == null) {' . chr(10) . ' return null;' . chr(10) . ' }' . chr(10) . ' return o.pop();' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.shift = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' if (o.length == null) {' . chr(10) . ' return null;' . chr(10) . ' }' . chr(10) . ' return o.shift();' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.push = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' var v = List__[1];' . chr(10) . ' for(var i = 0; i < v.length; i++) {' . chr(10) . ' o.push(v[i]);' . chr(10) . ' }' . chr(10) . ' return o.length;' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.unshift = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' var v = List__[1];' . chr(10) . ' for(var i = v.length-1; i >= 0; i--) {' . chr(10) . ' o.unshift(v[i]);' . chr(10) . ' }' . chr(10) . ' return o.length;' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.join = function(List__) {' . chr(10) . ' var s = List__[0];' . chr(10) . ' var o = List__[1];' . chr(10) . ' return o.join(s);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.index = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' var s = List__[1];' . chr(10) . ' try {' . chr(10) . ' return o.indexOf(s, p5num(List__[2]));' . chr(10) . ' }' . chr(10) . ' catch(err) {' . chr(10) . ' return -1;' . chr(10) . ' }' . chr(10) . '};' . chr(10) . 'CORE.rindex = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' var s = List__[1];' . chr(10) . ' try {' . chr(10) . ' if (List__.length > 2) {' . chr(10) . ' var i = p5num(List__[2]);' . chr(10) . ' if (i < 0) {' . chr(10) . ' if (s.length == 0) {' . chr(10) . ' return 0;' . chr(10) . ' }' . chr(10) . ' return -1;' . chr(10) . ' }' . chr(10) . ' return o.lastIndexOf(s, i);' . chr(10) . ' }' . chr(10) . ' return o.lastIndexOf(s);' . chr(10) . ' }' . chr(10) . ' catch(err) {' . chr(10) . ' return -1;' . chr(10) . ' }' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.length = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' if (typeof o.string === "function") {' . chr(10) . ' return o.string().length;' . chr(10) . ' }' . chr(10) . ' return o.length;' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.pack = function(List__) { CORE.warn([ "CORE::pack not implemented" ]) };' . chr(10) . 'CORE.unpack = function(List__) { CORE.warn([ "CORE::unpack not implemented" ]) };' . chr(10) . chr(10) . 'CORE.ref = function(List__) {' . chr(10) . ' var o = List__[0];' . chr(10) . ' if (o == null) {' . chr(10) . ' return "";' . chr(10) . ' }' . chr(10) . ' if (o._class_ && typeof o._class_._ref_ === "string") {' . chr(10) . ' // blessed reference' . chr(10) . ' return o._class_._ref_;' . chr(10) . ' }' . chr(10) . ' if (typeof o._ref_ === "string") {' . chr(10) . ' // un-blessed reference' . chr(10) . ' return o._ref_;' . chr(10) . ' }' . chr(10) . ' if (typeof o === "function") {' . chr(10) . ' return "CODE";' . chr(10) . ' }' . chr(10) . ' return "";' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.split = function(List__) {' . chr(10) . ' var pattern = List__[0];' . chr(10) . ' var s = List__[1];' . chr(10) . ' var limit = List__[2];' . chr(10) . ' if (typeof pattern === "string") {' . chr(10) . ' if (pattern == " ") {' . chr(10) . ' var res = [];' . chr(10) . ' for (var i_ = 0, a_ = s.split(/(?: |' . chr(92) . 'n)+/); i_ < a_.length ; i_++) {' . chr(10) . ' if (a_[i_] != "") {' . chr(10) . ' res.push(a_[i_])' . chr(10) . ' }' . chr(10) . ' }' . chr(10) . ' return res;' . chr(10) . ' }' . chr(10) . ' return s.split(pattern);' . chr(10) . ' }' . chr(10) . ' CORE.die(["not implemented"]);' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.prototype = function(List__, data) {' . chr(10) . ' var name = List__[0];' . chr(10) . ' // TODO - fully qualify "name" using information from "data"' . chr(10) . ' // XXX - lookup in CORE::GLOBAL?' . chr(10) . ' p5pkg["Perlito5"].v_PROTO._hash_[name] || p5pkg["Perlito5"].v_CORE_PROTO._hash_[name]' . chr(10) . '};' . chr(10) . chr(10))))
};
1;
@@ -9167,6 +9167,18 @@ sub Perlito5::Javascript::IO::emit_javascript {
;
package main;
undef();
+package Perlito5::Javascript::Sprintf;
+sub Perlito5::Javascript::Sprintf::emit_javascript {
+ return ((('/**' . chr(10) . ' * Copyright (c) 2010 Jakob Westhoff' . chr(10) . ' *' . chr(10) . ' * Permission is hereby granted, free of charge, to any person obtaining a copy' . chr(10) . ' * of this software and associated documentation files (the "Software"), to deal' . chr(10) . ' * in the Software without restriction, including without limitation the rights' . chr(10) . ' * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell' . chr(10) . ' * copies of the Software, and to permit persons to whom the Software is' . chr(10) . ' * furnished to do so, subject to the following conditions:' . chr(10) . ' * ' . chr(10) . ' * The above copyright notice and this permission notice shall be included in' . chr(10) . ' * all copies or substantial portions of the Software.' . chr(10) . ' * ' . chr(10) . ' * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR' . chr(10) . ' * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,' . chr(10) . ' * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE' . chr(10) . ' * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER' . chr(10) . ' * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,' . chr(10) . ' * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN' . chr(10) . ' * THE SOFTWARE.' . chr(10) . ' */' . chr(10) . chr(10) . 'CORE.sprintf = function(List__) {' . chr(10) . ' var format = List__[0];' . chr(10) . ' var list = List__[1];' . chr(10) . chr(10) . ' // Check for format definition' . chr(10) . ' if ( typeof format != ' . chr(39) . 'string' . chr(39) . ' ) {' . chr(10) . ' CORE.die(["sprintf: The first arguments need to be a valid format string."]);' . chr(10) . ' }' . chr(10) . ' ' . chr(10) . ' /**' . chr(10) . ' * Define the regex to match a formating string' . chr(10) . ' * The regex consists of the following parts:' . chr(10) . ' * percent sign to indicate the start' . chr(10) . ' * (optional) sign specifier' . chr(10) . ' * (optional) padding specifier' . chr(10) . ' * (optional) alignment specifier' . chr(10) . ' * (optional) width specifier' . chr(10) . ' * (optional) precision specifier' . chr(10) . ' * type specifier:' . chr(10) . ' * % - literal percent sign' . chr(10) . ' * b - binary number' . chr(10) . ' * c - ASCII character represented by the given value' . chr(10) . ' * d - signed decimal number' . chr(10) . ' * f - floating point value' . chr(10) . ' * o - octal number' . chr(10) . ' * s - string' . chr(10) . ' * x - hexadecimal number (lowercase characters)' . chr(10) . ' * X - hexadecimal number (uppercase characters)' . chr(10) . ' */' . chr(10) . ' var r = new RegExp( /%(' . chr(92) . '+)?([0 ]|' . chr(39) . '(.))?(-)?([0-9]+)?(' . chr(92) . '.([0-9]+))?([%bcdfosxX])/g );' . chr(10) . chr(10) . ' /**' . chr(10) . ' * Each format string is splitted into the following parts:' . chr(10) . ' * 0: Full format string' . chr(10) . ' * 1: sign specifier (+)' . chr(10) . ' * 2: padding specifier (0/<space>/' . chr(39) . '<any char>)' . chr(10) . ' * 3: if the padding character starts with a ' . chr(39) . ' this will be the real ' . chr(10) . ' * padding character' . chr(10) . ' * 4: alignment specifier' . chr(10) . ' * 5: width specifier' . chr(10) . ' * 6: precision specifier including the dot' . chr(10) . ' * 7: precision specifier without the dot' . chr(10) . ' * 8: type specifier' . chr(10) . ' */' . chr(10) . ' var parts = [];' . chr(10) . ' var paramIndex = 0;' . chr(10) . ' while ( part = r.exec( format ) ) {' . chr(10) . ' // Check if an input value has been provided, for the current' . chr(10) . ' // format string' . chr(10) . ' if ( paramIndex >= list.length ) {' . chr(10) . ' CORE.die(["sprintf: At least one argument was missing."]);' . chr(10) . ' }' . chr(10) . chr(10) . ' parts[parts.length] = {' . chr(10) . ' /* beginning of the part in the string */' . chr(10) . ' begin: part.index,' . chr(10) . ' /* end of the part in the string */' . chr(10) . ' end: part.index + part[0].length,' . chr(10) . ' /* force sign */' . chr(10) . ' sign: ( part[1] == ' . chr(39) . '+' . chr(39) . ' ),' . chr(10) . ' /* is the given data negative */' . chr(10) . ' negative: ( parseInt( list[paramIndex] ) < 0 ) ? true : false,' . chr(10) . ' /* padding character (default: <space>) */' . chr(10) . ' padding: ( part[2] == undefined )' . chr(10) . ' ? ( ' . chr(39) . ' ' . chr(39) . ' ) /* default */' . chr(10) . ' : ( ( part[2].substring( 0, 1 ) == "' . chr(39) . '" ) ' . chr(10) . ' ? ( part[3] ) /* use special char */' . chr(10) . ' : ( part[2] ) /* use normal <space> or zero */' . chr(10) . ' ),' . chr(10) . ' /* should the output be aligned left?*/' . chr(10) . ' alignLeft: ( part[4] == ' . chr(39) . '-' . chr(39) . ' ),' . chr(10) . ' /* width specifier (number or false) */' . chr(10) . ' width: ( part[5] != undefined ) ? part[5] : false,' . chr(10) . ' /* precision specifier (number or false) */' . chr(10) . ' precision: ( part[7] != undefined ) ? part[7] : false,' . chr(10) . ' /* type specifier */' . chr(10) . ' type: part[8],' . chr(10) . ' /* the given data associated with this part converted to a string */' . chr(10) . ' data: ( part[8] != ' . chr(39) . '%' . chr(39) . ' ) ? String ( list[paramIndex++] ) : false' . chr(10) . ' };' . chr(10) . ' }' . chr(10) . chr(10) . ' var newString = "";' . chr(10) . ' var start = 0;' . chr(10) . ' // Generate our new formated string' . chr(10) . ' for( var i=0; i<parts.length; ++i ) {' . chr(10) . ' // Add first unformated string part' . chr(10) . ' newString += format.substring( start, parts[i].begin );' . chr(10) . ' ' . chr(10) . ' // Mark the new string start' . chr(10) . ' start = parts[i].end;' . chr(10) . chr(10) . ' // Create the appropriate preformat substitution' . chr(10) . ' // This substitution is only the correct type conversion. All the' . chr(10) . ' // different options and flags haven' . chr(39) . 't been applied to it at this' . chr(10) . ' // point' . chr(10) . ' var preSubstitution = "";' . chr(10) . ' switch ( parts[i].type ) {' . chr(10) . ' case ' . chr(39) . '%' . chr(39) . ':' . chr(10) . ' preSubstitution = "%";' . chr(10) . ' break;' . chr(10) . ' case ' . chr(39) . 'b' . chr(39) . ':' . chr(10) . ' preSubstitution = Math.abs( parseInt( parts[i].data ) ).toString( 2 );' . chr(10) . ' break;' . chr(10) . ' case ' . chr(39) . 'c' . chr(39) . ':' . chr(10) . ' preSubstitution = String.fromCharCode( Math.abs( parseInt( parts[i].data ) ) );' . chr(10) . ' break;' . chr(10) . ' case ' . chr(39) . 'd' . chr(39) . ':' . chr(10) . ' preSubstitution = String( Math.abs( parseInt( parts[i].data ) ) );' . chr(10) . ' break;' . chr(10) . ' case ' . chr(39) . 'f' . chr(39) . ':' . chr(10) . ' preSubstitution = ( parts[i].precision == false )' . chr(10) . ' ? ( String( ( Math.abs( parseFloat( parts[i].data ) ) ) ) )' . chr(10) . ' : ( Math.abs( parseFloat( parts[i].data ) ).toFixed( parts[i].precision ) );' . chr(10) . ' break;' . chr(10) . ' case ' . chr(39) . 'o' . chr(39) . ':' . chr(10) . ' preSubstitution = Math.abs( parseInt( parts[i].data ) ).toString( 8 );' . chr(10) . ' break;' . chr(10) . ' case ' . chr(39) . 's' . chr(39) . ':' . chr(10) . ' preSubstitution = parts[i].data.substring( 0, parts[i].precision ? parts[i].precision : parts[i].data.length ); /* Cut if precision is defined */' . chr(10) . ' break;' . chr(10) . ' case ' . chr(39) . 'x' . chr(39) . ':' . chr(10) . ' preSubstitution = Math.abs( parseInt( parts[i].data ) ).toString( 16 ).toLowerCase();' . chr(10) . ' break;' . chr(10) . ' case ' . chr(39) . 'X' . chr(39) . ':' . chr(10) . ' preSubstitution = Math.abs( parseInt( parts[i].data ) ).toString( 16 ).toUpperCase();' . chr(10) . ' break;' . chr(10) . ' default:' . chr(10) . ' throw ' . chr(39) . 'sprintf: Unknown type "' . chr(39) . ' + parts[i].type + ' . chr(39) . '" detected. This should never happen. Maybe the regex is wrong.' . chr(39) . ';' . chr(10) . ' }' . chr(10) . chr(10) . ' // The % character is a special type and does not need further processing' . chr(10) . ' if ( parts[i].type == "%" ) {' . chr(10) . ' newString += preSubstitution;' . chr(10) . ' continue;' . chr(10) . ' }' . chr(10) . chr(10) . ' // Modify the preSubstitution by taking sign, padding and width' . chr(10) . ' // into account' . chr(10) . chr(10) . ' // Pad the string based on the given width' . chr(10) . ' if ( parts[i].width != false ) {' . chr(10) . ' // Padding needed?' . chr(10) . ' if ( parts[i].width > preSubstitution.length ) ' . chr(10) . ' {' . chr(10) . ' var origLength = preSubstitution.length;' . chr(10) . ' for( var j = 0; j < parts[i].width - origLength; ++j ) ' . chr(10) . ' {' . chr(10) . ' preSubstitution = ( parts[i].alignLeft == true ) ' . chr(10) . ' ? ( preSubstitution + parts[i].padding )' . chr(10) . ' : ( parts[i].padding + preSubstitution );' . chr(10) . ' }' . chr(10) . ' }' . chr(10) . ' }' . chr(10) . chr(10) . ' // Add a sign symbol if neccessary or enforced, but only if we are' . chr(10) . ' // not handling a string' . chr(10) . ' if ( parts[i].type == ' . chr(39) . 'b' . chr(39) . ' ' . chr(10) . ' || parts[i].type == ' . chr(39) . 'd' . chr(39) . ' ' . chr(10) . ' || parts[i].type == ' . chr(39) . 'o' . chr(39) . ' ' . chr(10) . ' || parts[i].type == ' . chr(39) . 'f' . chr(39) . ' ' . chr(10) . ' || parts[i].type == ' . chr(39) . 'x' . chr(39) . ' ' . chr(10) . ' || parts[i].type == ' . chr(39) . 'X' . chr(39) . ' ) {' . chr(10) . ' if ( parts[i].negative == true ) {' . chr(10) . ' preSubstitution = "-" + preSubstitution;' . chr(10) . ' }' . chr(10) . ' else if ( parts[i].sign == true ) {' . chr(10) . ' preSubstitution = "+" + preSubstitution;' . chr(10) . ' }' . chr(10) . ' }' . chr(10) . chr(10) . ' // Add the substitution to the new string' . chr(10) . ' newString += preSubstitution;' . chr(10) . ' }' . chr(10) . chr(10) . ' // Add the last part of the given format string, which may still be there' . chr(10) . ' newString += format.substring( start, format.length );' . chr(10) . chr(10) . ' return newString;' . chr(10) . '};' . chr(10) . chr(10) . 'CORE.printf = function(List__) {' . chr(10) . ' return CORE.print([ CORE.sprintf(List__) ]);' . chr(10) . '};' . chr(10) . chr(10))))
+};
+1;
+
+;
+
+# use Perlito5::Javascript::Sprintf
+;
+package main;
+undef();
package Perlito5::AST::Apply;
((my %op) = ('infix:<+=>', 'infix:<+>', 'infix:<-=>', 'infix:<->', 'infix:<*=>', 'infix:<*>', 'infix:</=>', 'infix:</>', 'infix:<||=>', 'infix:<||>', 'infix:<&&=>', 'infix:<&&>', 'infix:<|=>', 'infix:<|>', 'infix:<&=>', 'infix:<&>', 'infix:<//=>', 'infix:<//>', 'infix:<.=>', 'list:<.>'));
sub Perlito5::AST::Apply::op_assign {
@@ -10179,7 +10191,7 @@ package Perlito5::Runtime;
push(@INC, $_ )
};
($Perlito5::SPECIAL_VAR = {'$_', 'ARG', '$&', '$MATCH', '$`', '$PREMATCH', '$' . chr(39), '$POSTMATCH', '$+', '$LAST_PAREN_MATCH', '@+', '@LAST_MATCH_END', '%+', '%LAST_PAREN_MATCH', '@-', '@LAST_MATCH_START', '$|', 'autoflush', '$/', '$RS', '@_', '@ARG', '< $', '$EUID', '$.', '$NR', '< $< ', '$UID', '$(', '$GID', '$#', undef(), '$@', '$EVAL_ERROR', '$=', '$FORMAT_LINES_PER_PAGE', '$,', '$OFS', '$?', '$CHILD_ERROR', '$*', undef(), '$[', undef(), '$$', '$PID', '%-', undef(), '$~', '$FORMAT_NAME', '$-', '$FORMAT_LINES_LEFT', '$&', '$MATCH', '$%', '$FORMAT_PAGE_NUMBER', '$)', '$EGID', '$]', undef(), '$!', '$ERRNO', '$;', '$SUBSEP', '$' . chr(92), '$ORS', '%!', undef(), '$"', '$LIST_SEPARATOR', '$_', '$ARG', '$:', 'FORMAT_LINE_BREAK_CHARACTERS'});
-($Perlito5::CORE_PROTO = {'CORE::shutdown', '*$', 'CORE::chop', undef(), 'CORE::lstat', '*', 'CORE::rename', '$$', 'CORE::lock', chr(92) . '$', 'CORE::rand', ';$', 'CORE::gmtime', ';$', 'CORE::gethostbyname', '$', 'CORE::each', chr(92) . '[@%]', 'CORE::ref', '_', 'CORE::syswrite', '*$;$$', 'CORE::msgctl', '$$$', 'CORE::getnetbyname', '$', 'CORE::write', ';*', 'CORE::alarm', '_', 'CORE::print', undef(), 'CORE::getnetent', '', 'CORE::semget', '$$$', 'CORE::use', undef(), 'CORE::abs', '_', 'CORE::break', '', 'CORE::undef', undef(), 'CORE::no', undef(), 'CORE::eval', undef(), 'CORE::split', undef(), 'CORE::localtime', ';$', 'CORE::sort', undef(), 'CORE::chown', '@', 'CORE::endpwent', '', 'CORE::getpwent', '', 'CORE::pos', undef(), 'CORE::lcfirst', '_', 'CORE::kill', '@', 'CORE::send', '*$$;$', 'CORE::endprotoent', '', 'CORE::semctl', '$$$$', 'CORE::waitpid', '$$', 'CORE::utime', '@', 'CORE::dbmclose', chr(92) . '%', 'CORE::getpwnam', '$', 'CORE::substr', '$$;$$', 'CORE::listen', '*$', 'CORE::getprotoent', '', 'CORE::shmget', '$$$', 'CORE::our', undef(), 'CORE::readlink', '_', 'CORE::shmwrite', '$$$$', 'CORE::times', '', 'CORE::package', undef(), 'CORE::map', undef(), 'CORE::join', '$@', 'CORE::rmdir', '_', 'CORE::shmread', '$$$$', 'CORE::uc', '_', 'CORE::bless', '$;$', 'CORE::closedir', '*', 'CORE::getppid', '', 'CORE::tie', undef(), 'CORE::readdir', '*', 'CORE::gethostent', '', 'CORE::getlogin', '', 'CORE::last', undef(), 'CORE::gethostbyaddr', '$$', 'CORE::accept', '**', 'CORE::log', '_', 'CORE::tell', ';*', 'CORE::readline', ';*', 'CORE::tied', undef(), 'CORE::socket', '*$$$', 'CORE::umask', ';$', 'CORE::sysread', '*' . chr(92) . '$$;$', 'CORE::syscall', '$@', 'CORE::quotemeta', '_', 'CORE::dump', '', 'CORE::opendir', '*$', 'CORE::untie', undef(), 'CORE::truncate', '$$', 'CORE::select', ';*', 'CORE::sleep', ';$', 'CORE::seek', '*$$', 'CORE::read', '*' . chr(92) . '$$;$', 'CORE::rewinddir', '*', 'CORE::scalar', undef(), 'CORE::wantarray', '', 'CORE::oct', '_', 'CORE::bind', '*$', 'CORE::stat', '*', 'CORE::sqrt', '_', 'CORE::getc', ';*', 'CORE::fileno', '*', 'CORE::getpeername', '*', 'CORE::sin', '_', 'CORE::getnetbyaddr', '$$', 'CORE::grep', undef(), 'CORE::setservent', '$', 'CORE::sub', undef(), 'CORE::shmctl', '$$$', 'CORE::study', undef(), 'CORE::msgrcv', '$$$$$', 'CORE::setsockopt', '*$$$', 'CORE::int', '_', 'CORE::pop', ';' . chr(92) . '@', 'CORE::link', '$$', 'CORE::exec', undef(), 'CORE::setpwent', '', 'CORE::mkdir', '_;$', 'CORE::sysseek', '*$$', 'CORE::endservent', '', 'CORE::chr', '_', 'CORE::when', undef(), 'CORE::getpwuid', '$', 'CORE::setprotoent', '$', 'CORE::reverse', '@', 'CORE::say', undef(), 'CORE::goto', undef(), 'CORE::getgrent', '', 'CORE::endnetent', '', 'CORE::hex', '_', 'CORE::binmode', '*;$', 'CORE::formline', '$@', 'CORE::getgrnam', '$', 'CORE::ucfirst', '_', 'CORE::chdir', ';$', 'CORE::setnetent', '$', 'CORE::splice', chr(92) . '@;$$@', 'CORE::unlink', '@', 'CORE::time', '', 'CORE::push', chr(92) . '@@', 'CORE::exit', ';$', 'CORE::endgrent', '', 'CORE::unshift', chr(92) . '@@', 'CORE::local', undef(), 'CORE::my', undef(), 'CORE::cos', '_', 'CORE::redo', undef(), 'CORE::warn', '@', 'CORE::getsockname', '*', 'CORE::pipe', '**', 'CORE::sprintf', '$@', 'CORE::open', '*;$@', 'CORE::setpgrp', ';$$', 'CORE::exp', '_', 'CORE::seekdir', '*$', 'CORE::getservbyport', '$$', 'CORE::given', undef(), 'CORE::pack', '$@', 'CORE::msgget', '$$', 'CORE::rindex', '$$;$', 'CORE::srand', ';$', 'CORE::telldir', '*', 'CORE::connect', '*$', 'CORE::getprotobyname', '$', 'CORE::msgsnd', '$$$', 'CORE::length', '_', 'CORE::state', undef(), 'CORE::die', '@', 'CORE::delete', undef(), 'CORE::getservent', '', 'CORE::getservbyname', '$$', 'CORE::setpriority', '$$$', 'CORE::lc', '_', 'CORE::fcntl', '*$$', 'CORE::chroot', '_', 'CORE::recv', '*' . chr(92) . '$$$', 'CORE::dbmopen', chr(92) . '%$$', 'CORE::socketpair', '**$$$', 'CORE::vec', '$$$', 'CORE::system', undef(), 'CORE::defined', '_', 'CORE::index', '$$;$', 'CORE::caller', ';$', 'CORE::close', ';*', 'CORE::atan2', '$$', 'CORE::semop', '$$', 'CORE::unpack', '$;$', 'CORE::ord', '_', 'CORE::chmod', '@', 'CORE::prototype', undef(), 'CORE::getprotobynumber', '$', 'CORE::values', chr(92) . '[@%]', 'CORE::chomp', undef(), 'CORE::ioctl', '*$$', 'CORE::eof', ';*', 'CORE::crypt', '$$', 'CORE::do', undef(), 'CORE::flock', '*$', 'CORE::wait', '', 'CORE::sethostent', '$', 'CORE::return', undef(), 'CORE::getsockopt', '*$$', 'CORE::fork', '', 'CORE::require', undef(), 'CORE::format', undef(), 'CORE::readpipe', '_', 'CORE::endhostent', '', 'CORE::getpgrp', ';$', 'CORE::setgrent', '', 'CORE::keys', chr(92) . '[@%]', 'CORE::glob', undef(), 'CORE::getpriority', '$$', 'CORE::reset', ';$', 'CORE::sysopen', '*$$;$', 'CORE::continue', '', 'CORE::next', undef(), 'CORE::getgrgid', '$', 'CORE::default', undef(), 'CORE::shift', ';' . chr(92) . '@', 'CORE::symlink', '$$', 'CORE::exists', '$', 'CORE::printf', undef()});
+($Perlito5::CORE_PROTO = {'CORE::shutdown', '*$', 'CORE::chop', undef(), 'CORE::lstat', '*', 'CORE::rename', '$$', 'CORE::lock', chr(92) . '$', 'CORE::rand', ';$', 'CORE::gmtime', ';$', 'CORE::gethostbyname', '$', 'CORE::each', chr(92) . '[@%]', 'CORE::ref', '_', 'CORE::syswrite', '*$;$$', 'CORE::msgctl', '$$$', 'CORE::getnetbyname', '$', 'CORE::write', ';*', 'CORE::alarm', '_', 'CORE::print', undef(), 'CORE::getnetent', '', 'CORE::semget', '$$$', 'CORE::use', undef(), 'CORE::abs', '_', 'CORE::break', '', 'CORE::undef', undef(), 'CORE::no', undef(), 'CORE::eval', undef(), 'CORE::split', undef(), 'CORE::localtime', ';$', 'CORE::sort', undef(), 'CORE::chown', '@', 'CORE::endpwent', '', 'CORE::getpwent', '', 'CORE::pos', undef(), 'CORE::lcfirst', '_', 'CORE::kill', '@', 'CORE::send', '*$$;$', 'CORE::endprotoent', '', 'CORE::semctl', '$$$$', 'CORE::waitpid', '$$', 'CORE::utime', '@', 'CORE::dbmclose', chr(92) . '%', 'CORE::getpwnam', '$', 'CORE::substr', '$$;$$', 'CORE::listen', '*$', 'CORE::getprotoent', '', 'CORE::shmget', '$$$', 'CORE::our', undef(), 'CORE::readlink', '_', 'CORE::shmwrite', '$$$$', 'CORE::times', '', 'CORE::package', undef(), 'CORE::map', undef(), 'CORE::join', '$@', 'CORE::rmdir', '_', 'CORE::shmread', '$$$$', 'CORE::uc', '_', 'CORE::bless', '$;$', 'CORE::closedir', '*', 'CORE::getppid', '', 'CORE::tie', undef(), 'CORE::readdir', '*', 'CORE::gethostent', '', 'CORE::getlogin', '', 'CORE::last', undef(), 'CORE::gethostbyaddr', '$$', 'CORE::accept', '**', 'CORE::log', '_', 'CORE::tell', ';*', 'CORE::readline', ';*', 'CORE::tied', undef(), 'CORE::socket', '*$$$', 'CORE::umask', ';$', 'CORE::sysread', '*' . chr(92) . '$$;$', 'CORE::syscall', '$@', 'CORE::quotemeta', '_', 'CORE::dump', '', 'CORE::opendir', '*$', 'CORE::untie', undef(), 'CORE::truncate', '$$', 'CORE::select', ';*', 'CORE::sleep', ';$', 'CORE::seek', '*$$', 'CORE::read', '*' . chr(92) . '$$;$', 'CORE::rewinddir', '*', 'CORE::scalar', undef(), 'CORE::wantarray', '', 'CORE::oct', '_', 'CORE::bind', '*$', 'CORE::stat', '*', 'CORE::sqrt', '_', 'CORE::getc', ';*', 'CORE::fileno', '*', 'CORE::getpeername', '*', 'CORE::sin', '_', 'CORE::getnetbyaddr', '$$', 'CORE::grep', undef(), 'CORE::setservent', '$', 'CORE::sub', undef(), 'CORE::shmctl', '$$$', 'CORE::study', undef(), 'CORE::msgrcv', '$$$$$', 'CORE::setsockopt', '*$$$', 'CORE::int', '_', 'CORE::pop', ';' . chr(92) . '@', 'CORE::link', '$$', 'CORE::exec', undef(), 'CORE::setpwent', '', 'CORE::mkdir', '_;$', 'CORE::sysseek', '*$$', 'CORE::endservent', '', 'CORE::chr', '_', 'CORE::when', undef(), 'CORE::getpwuid', '$', 'CORE::setprotoent', '$', 'CORE::reverse', '@', 'CORE::say', undef(), 'CORE::goto', undef(), 'CORE::getgrent', '', 'CORE::endnetent', '', 'CORE::hex', '_', 'CORE::binmode', '*;$', 'CORE::formline', '$@', 'CORE::getgrnam', '$', 'CORE::ucfirst', '_', 'CORE::chdir', ';$', 'CORE::setnetent', '$', 'CORE::splice', chr(92) . '@;$$@', 'CORE::unlink', '@', 'CORE::time', '', 'CORE::push', chr(92) . '@@', 'CORE::exit', ';$', 'CORE::endgrent', '', 'CORE::unshift', chr(92) . '@@', 'CORE::local', undef(), 'CORE::my', undef(), 'CORE::cos', '_', 'CORE::redo', undef(), 'CORE::warn', '@', 'CORE::getsockname', '*', 'CORE::pipe', '**', 'CORE::sprintf', '$@', 'CORE::open', '*;$@', 'CORE::setpgrp', ';$$', 'CORE::exp', '_', 'CORE::seekdir', '*$', 'CORE::getservbyport', '$$', 'CORE::given', undef(), 'CORE::pack', '$@', 'CORE::msgget', '$$', 'CORE::rindex', '$$;$', 'CORE::srand', ';$', 'CORE::telldir', '*', 'CORE::connect', '*$', 'CORE::getprotobyname', '$', 'CORE::msgsnd', '$$$', 'CORE::length', '_', 'CORE::state', undef(), 'CORE::die', '@', 'CORE::delete', undef(), 'CORE::getservent', '', 'CORE::getservbyname', '$$', 'CORE::setpriority', '$$$', 'CORE::lc', '_', 'CORE::fcntl', '*$$', 'CORE::chroot', '_', 'CORE::recv', '*' . chr(92) . '$$$', 'CORE::dbmopen', chr(92) . '%$$', 'CORE::socketpair', '**$$$', 'CORE::vec', '$$$', 'CORE::system', undef(), 'CORE::defined', '_', 'CORE::index', '$$;$', 'CORE::caller', ';$', 'CORE::close', ';*', 'CORE::atan2', '$$', 'CORE::semop', '$$', 'CORE::unpack', '$;$', 'CORE::ord', '_', 'CORE::chmod', '@', 'CORE::prototype', undef(), 'CORE::getprotobynumber', '$', 'CORE::values', chr(92) . '[@%]', 'CORE::chomp', undef(), 'CORE::ioctl', '*$$', 'CORE::eof', ';*', 'CORE::crypt', '$$', 'CORE::do', undef(), 'CORE::flock', '*$', 'CORE::wait', '', 'CORE::sethostent', '$', 'CORE::return', undef(), 'CORE::getsockopt', '*$$', 'CORE::fork', '', 'CORE::require', undef(), 'CORE::format', undef(), 'CORE::readpipe', '_', 'CORE::endhostent', '', 'CORE::getpgrp', ';$', 'CORE::setgrent', '', 'CORE::keys', chr(92) . '[@%]', 'CORE::glob', undef(), 'CORE::getpriority', '$$', 'CORE::reset', ';$', 'CORE::sysopen', '*$$;$', 'CORE::continue', '', 'CORE::next', undef(), 'CORE::getgrgid', '$', 'CORE::default', undef(), 'CORE::shift', ';' . chr(92) . '@', 'CORE::symlink', '$$', 'CORE::exists', '$', 'CORE::printf', '$@'});
1;
;
@@ -10344,7 +10356,8 @@ package Perlito5::Runtime;
if ($expand_use) {
print(Perlito5::Javascript::Runtime->emit_javascript());
print(Perlito5::Javascript::CORE->emit_javascript());
- print(Perlito5::Javascript::IO->emit_javascript())
+ print(Perlito5::Javascript::IO->emit_javascript());
+ print(Perlito5::Javascript::Sprintf->emit_javascript())
};
print(Perlito5::AST::CompUnit::emit_javascript_program($comp_units))
};
View
1  src5/lib/Perlito5/Javascript/CORE.pm
@@ -341,7 +341,6 @@ CORE.length = function(List__) {
CORE.pack = function(List__) { CORE.warn([ "CORE::pack not implemented" ]) };
CORE.unpack = function(List__) { CORE.warn([ "CORE::unpack not implemented" ]) };
-CORE.sprintf = function(List__) { CORE.warn([ "CORE::sprintf not implemented" ]) };
CORE.ref = function(List__) {
var o = List__[0];
View
219 src5/lib/Perlito5/Javascript/Sprintf.pm
@@ -0,0 +1,219 @@
+use v5;
+
+package Perlito5::Javascript::Sprintf;
+
+sub emit_javascript {
+
+ return <<'EOT';
+/**
+ * Copyright (c) 2010 Jakob Westhoff
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+
+CORE.sprintf = function(List__) {
+ var format = List__[0];
+ var list = List__[1];
+
+ // Check for format definition
+ if ( typeof format != 'string' ) {
+ CORE.die(["sprintf: The first arguments need to be a valid format string."]);
+ }
+
+ /**
+ * Define the regex to match a formating string
+ * The regex consists of the following parts:
+ * percent sign to indicate the start
+ * (optional) sign specifier
+ * (optional) padding specifier
+ * (optional) alignment specifier
+ * (optional) width specifier
+ * (optional) precision specifier
+ * type specifier:
+ * % - literal percent sign
+ * b - binary number
+ * c - ASCII character represented by the given value
+ * d - signed decimal number
+ * f - floating point value
+ * o - octal number
+ * s - string
+ * x - hexadecimal number (lowercase characters)
+ * X - hexadecimal number (uppercase characters)
+ */
+ var r = new RegExp( /%(\+)?([0 ]|'(.))?(-)?([0-9]+)?(\.([0-9]+))?([%bcdfosxX])/g );
+
+ /**
+ * Each format string is splitted into the following parts:
+ * 0: Full format string
+ * 1: sign specifier (+)
+ * 2: padding specifier (0/<space>/'<any char>)
+ * 3: if the padding character starts with a ' this will be the real
+ * padding character
+ * 4: alignment specifier
+ * 5: width specifier
+ * 6: precision specifier including the dot
+ * 7: precision specifier without the dot
+ * 8: type specifier
+ */
+ var parts = [];
+ var paramIndex = 0;
+ while ( part = r.exec( format ) ) {
+ // Check if an input value has been provided, for the current
+ // format string
+ if ( paramIndex >= list.length ) {
+ CORE.die(["sprintf: At least one argument was missing."]);
+ }
+
+ parts[parts.length] = {
+ /* beginning of the part in the string */
+ begin: part.index,
+ /* end of the part in the string */
+ end: part.index + part[0].length,
+ /* force sign */
+ sign: ( part[1] == '+' ),
+ /* is the given data negative */
+ negative: ( parseInt( list[paramIndex] ) < 0 ) ? true : false,
+ /* padding character (default: <space>) */
+ padding: ( part[2] == undefined )
+ ? ( ' ' ) /* default */
+ : ( ( part[2].substring( 0, 1 ) == "'" )
+ ? ( part[3] ) /* use special char */
+ : ( part[2] ) /* use normal <space> or zero */
+ ),
+ /* should the output be aligned left?*/
+ alignLeft: ( part[4] == '-' ),
+ /* width specifier (number or false) */
+ width: ( part[5] != undefined ) ? part[5] : false,
+ /* precision specifier (number or false) */
+ precision: ( part[7] != undefined ) ? part[7] : false,
+ /* type specifier */
+ type: part[8],
+ /* the given data associated with this part converted to a string */
+ data: ( part[8] != '%' ) ? String ( list[paramIndex++] ) : false
+ };
+ }
+
+ var newString = "";
+ var start = 0;
+ // Generate our new formated string
+ for( var i=0; i<parts.length; ++i ) {
+ // Add first unformated string part
+ newString += format.substring( start, parts[i].begin );
+
+ // Mark the new string start
+ start = parts[i].end;
+
+ // Create the appropriate preformat substitution
+ // This substitution is only the correct type conversion. All the
+ // different options and flags haven't been applied to it at this
+ // point
+ var preSubstitution = "";
+ switch ( parts[i].type ) {
+ case '%':
+ preSubstitution = "%";
+ break;
+ case 'b':
+ preSubstitution = Math.abs( parseInt( parts[i].data ) ).toString( 2 );
+ break;
+ case 'c':
+ preSubstitution = String.fromCharCode( Math.abs( parseInt( parts[i].data ) ) );
+ break;
+ case 'd':
+ preSubstitution = String( Math.abs( parseInt( parts[i].data ) ) );
+ break;
+ case 'f':
+ preSubstitution = ( parts[i].precision == false )
+ ? ( String( ( Math.abs( parseFloat( parts[i].data ) ) ) ) )
+ : ( Math.abs( parseFloat( parts[i].data ) ).toFixed( parts[i].precision ) );
+ break;
+ case 'o':
+ preSubstitution = Math.abs( parseInt( parts[i].data ) ).toString( 8 );
+ break;
+ case 's':
+ preSubstitution = parts[i].data.substring( 0, parts[i].precision ? parts[i].precision : parts[i].data.length ); /* Cut if precision is defined */
+ break;
+ case 'x':
+ preSubstitution = Math.abs( parseInt( parts[i].data ) ).toString( 16 ).toLowerCase();
+ break;
+ case 'X':
+ preSubstitution = Math.abs( parseInt( parts[i].data ) ).toString( 16 ).toUpperCase();
+ break;
+ default:
+ throw 'sprintf: Unknown type "' + parts[i].type + '" detected. This should never happen. Maybe the regex is wrong.';
+ }
+
+ // The % character is a special type and does not need further processing
+ if ( parts[i].type == "%" ) {
+ newString += preSubstitution;
+ continue;
+ }
+
+ // Modify the preSubstitution by taking sign, padding and width
+ // into account
+
+ // Pad the string based on the given width
+ if ( parts[i].width != false ) {
+ // Padding needed?
+ if ( parts[i].width > preSubstitution.length )
+ {
+ var origLength = preSubstitution.length;
+ for( var j = 0; j < parts[i].width - origLength; ++j )
+ {
+ preSubstitution = ( parts[i].alignLeft == true )
+ ? ( preSubstitution + parts[i].padding )
+ : ( parts[i].padding + preSubstitution );
+ }
+ }
+ }
+
+ // Add a sign symbol if neccessary or enforced, but only if we are
+ // not handling a string
+ if ( parts[i].type == 'b'
+ || parts[i].type == 'd'
+ || parts[i].type == 'o'
+ || parts[i].type == 'f'
+ || parts[i].type == 'x'
+ || parts[i].type == 'X' ) {
+ if ( parts[i].negative == true ) {
+ preSubstitution = "-" + preSubstitution;
+ }
+ else if ( parts[i].sign == true ) {
+ preSubstitution = "+" + preSubstitution;
+ }
+ }
+
+ // Add the substitution to the new string
+ newString += preSubstitution;
+ }
+
+ // Add the last part of the given format string, which may still be there
+ newString += format.substring( start, format.length );
+
+ return newString;
+};
+
+CORE.printf = function(List__) {
+ return CORE.print([ CORE.sprintf(List__) ]);
+};
+
+EOT
+} # end of emit_javascript()
+
+1;
+
View
2  src5/lib/Perlito5/Runtime.pm
@@ -271,7 +271,7 @@ $Perlito5::CORE_PROTO = {
'CORE::shift' => ';\\@',
'CORE::symlink' => '$$',
'CORE::exists' => '$', # original 'undef',
- 'CORE::printf' => undef
+ 'CORE::printf' => '$@', # original 'undef',
};
1;
View
2  src5/util/perlito5.pl
@@ -11,6 +11,7 @@ package Perlito;
use Perlito5::Javascript::Runtime;
use Perlito5::Javascript::CORE;
use Perlito5::Javascript::IO;
+use Perlito5::Javascript::Sprintf;
use Perlito5::Macro;
use Perlito5::Perl5::Emitter;
use Perlito5::Perl5::Runtime;
@@ -215,6 +216,7 @@ package Perlito;
print Perlito5::Javascript::Runtime->emit_javascript();
print Perlito5::Javascript::CORE->emit_javascript();
print Perlito5::Javascript::IO->emit_javascript();
+ print Perlito5::Javascript::Sprintf->emit_javascript();
}
print Perlito5::AST::CompUnit::emit_javascript_program( $comp_units );
}
Please sign in to comment.
Something went wrong with that request. Please try again.