/* * CDDL HEADER START * * The contents of this file are subject to the terms of the * Common Development and Distribution License, Version 1.0 only * (the "License"). You may not use this file except in compliance * with the License. * * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE * or http://www.opensolaris.org/os/licensing. * See the License for the specific language governing permissions * and limitations under the License. * * When distributing Covered Code, include this CDDL HEADER in each * file and include the License file at usr/src/OPENSOLARIS.LICENSE. * If applicable, add the following below this CDDL HEADER, with the * fields enclosed by brackets "[]" replaced with your own identifying * information: Portions Copyright [yyyy] [name of copyright owner] * * CDDL HEADER END */ /* * Copyright (c) 1999 by Sun Microsystems, Inc. * All rights reserved. */ #pragma ident "%Z%%M% %I% %E% SMI" #include #include #include #include #define DIGIT(x) (((x) > 9) ? ((x) + 'a' - 10) : ((x) + '0')) void to_digit(fcode_env_t *env) { CHECK_DEPTH(env, 1, ">digit"); TOS = DIGIT(TOS); } void pic_hold(fcode_env_t *env) { CHECK_DEPTH(env, 1, "hold"); *(--env->picturebufpos) = (char) POP(DS); } void pic_start(fcode_env_t *env) { env->picturebufpos = env->picturebuf + env->picturebuflen - 1; *env->picturebufpos = 0; } void pic_ustop(fcode_env_t *env) { CHECK_DEPTH(env, 1, "u#>"); (void) POP(DS); push_string(env, env->picturebufpos, strlen(env->picturebufpos)); } void pic_unsigned(fcode_env_t *env) { ufstack_t a, b; CHECK_DEPTH(env, 1, "u#"); a = (ufstack_t) TOS; b = a % env->num_base; TOS = (fstack_t) (a / env->num_base); *(--env->picturebufpos) = DIGIT(b); } void pic_sign(fcode_env_t *env) { fstack_t s; CHECK_DEPTH(env, 1, "sign"); s = POP(DS); if (s < 0) { PUSH(DS, '-'); pic_hold(env); } } static void pic_uremainder(fcode_env_t *env) { CHECK_DEPTH(env, 1, "u#s"); do { pic_unsigned(env); } while (TOS); } void format_number(fcode_env_t *env, int neg, int width) { pic_start(env); if (width == 0) { PUSH(DS, ' '); pic_hold(env); } pic_uremainder(env); if (env->num_base == 10 && neg) { PUSH(DS, '-'); pic_hold(env); } width -= strlen(env->picturebufpos); while (width > 0) { PUSH(DS, ' '); pic_hold(env); width--; } pic_ustop(env); } static void convert_num(fcode_env_t *env) { int n; CHECK_DEPTH(env, 1, "(.)"); n = 0; if (env->num_base == 10 && TOS < 0) { TOS = -TOS; n = 1; } format_number(env, n, 0); } void do_dot_r(fcode_env_t *env) { int w, n; CHECK_DEPTH(env, 2, ".r"); n = 0; w = (int) POP(DS); if (env->num_base == 10 && TOS < 0) { TOS = -TOS; n = 1; } format_number(env, n, w); type(env); } void do_udot_r(fcode_env_t *env) { int w; CHECK_DEPTH(env, 2, "u.r"); w = (int) POP(DS); format_number(env, 0, w); type(env); } void do_dot(fcode_env_t *env) { CHECK_DEPTH(env, 1, "."); PUSH(DS, 0); do_dot_r(env); } void do_dot_d(fcode_env_t *env) { int base; CHECK_DEPTH(env, 1, ".d"); base = env->num_base; env->num_base = 10; do_dot(env); env->num_base = base; } void do_dot_x(fcode_env_t *env) { int base; CHECK_DEPTH(env, 1, ".x"); base = env->num_base; env->num_base = 16; do_dot(env); env->num_base = base; } void do_udot(fcode_env_t *env) { CHECK_DEPTH(env, 1, "u."); PUSH(DS, 0); do_udot_r(env); } void pic_dunsigned(fcode_env_t *env) { ufstack_t b; u_dforth_t a; CHECK_DEPTH(env, 2, "#"); a = pop_double(env); b = a % env->num_base; a /= env->num_base; push_double(env, a); *(--env->picturebufpos) = DIGIT(b); } void pic_dremainder(fcode_env_t *env) { CHECK_DEPTH(env, 2, "#s"); do { pic_dunsigned(env); } while (peek_double(env)); } void pic_dstop(fcode_env_t *env) { CHECK_DEPTH(env, 2, "#>"); (void) pop_double(env); push_string(env, env->picturebufpos, strlen(env->picturebufpos)); } #pragma init(_init) static void _init(void) { fcode_env_t *env = initial_env; ASSERT(env); NOTICE; env->picturebuflen = 0x100; env->picturebuf = MALLOC(env->picturebuflen); ANSI(0x095, 0, "hold", pic_hold); ANSI(0x096, 0, "<#", pic_start); ANSI(0x097, 0, "u#>", pic_ustop); ANSI(0x098, 0, "sign", pic_sign); ANSI(0x099, 0, "u#", pic_unsigned); ANSI(0x09a, 0, "u#s", pic_uremainder); ANSI(0x09b, 0, "u.", do_udot); P1275(0x09c, 0, "u.r", do_udot_r); P1275(0x09d, 0, ".", do_dot); ANSI(0x09e, 0, ".r", do_dot_r); ANSI(0x0c7, 0, "#", pic_dunsigned); ANSI(0x0c8, 0, "#s", pic_dremainder); ANSI(0x0c9, 0, "#>", pic_dstop); FORTH(0, ">digit", to_digit); FORTH(0, "(.)", convert_num); FORTH(0, ".d", do_dot_d); FORTH(0, ".x", do_dot_x); }