<commit_before>/*
 * Twin - A Tiny Window System
 * Copyright © 2004 <NAME> <<EMAIL>>
 * All rights reserved.
 *
 * This Library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Library General Public License as
 * published by the Free Software Foundation; either version 2 of the
 * License, or (at your option) any later version.
 *
 * This Library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Library General Public License for more details.
 *
 * You should have received a copy of the GNU Library General Public
 * License along with the Twin Library; see the file COPYING.  If not,
 * write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
 * Boston, MA 02111-1307, USA.
 */

#include "twinint.h"

#if 0
#include <stdio.h>
#define F(f)	    twin_fixed_to_double(f)
#define DBGMSG(x)   printf x
#else
#define DBGMSG(x)
#endif

#define uint32_lo(i)	((i) & 0xffff)
#define uint32_hi(i)	((i) >> 16)
#define uint32_carry16	((1) << 16)

#if 0
twin_fixed_t
twin_fixed_mul (twin_fixed_t af, twin_fixed_t bf)
{
    uint32_t	    a;
    uint32_t	    b;
    uint16_t	    ah, al, bh, bl;
    uint32_t	    r0, r1, r2, r3;
    uint32_t	    hi, lo;
    twin_fixed_t    r;
    twin_bool_t	    negative = TWIN_FALSE;

    a = (uint32_t) af;
    b = (uint32_t) bf;
    if (af < 0)
    {
	negative = !negative;
	a = -a;
    }
    if (bf < 0)
    {
	negative = !negative;
	b = -b;
    }

    al = uint32_lo (a);
    ah = uint32_hi (a);
    bl = uint32_lo (b);
    bh = uint32_hi (b);

    r0 = (uint32_t) al * bl;
    r1 = (uint32_t) al * bh;
    r2 = (uint32_t) ah * bl;
    r3 = (uint32_t) ah * bh;

    r1 += uint32_hi(r0);    /* no carry possible */
    r1 += r2;		    /* but this can carry */
    if (r1 < r2)	    /* check */
	r3 += uint32_carry16;

    hi = r3 + uint32_hi(r1);
    lo = (uint32_lo (r1) << 16) + uint32_lo (r0);

    DBGMSG (("0x%x * 0x%x = 0x%x%08x\n", a, b, hi, lo));

    r = (twin_fixed_t) ((hi << 16) | (lo >> 16));
    if (negative)
	r = -r;
    DBGMSG (("%9.4f * %9.4f = %9.4f\n", 
	     twin_fixed_to_double(af), twin_fixed_to_double(bf),
	     twin_fixed_to_double (r)));
    return r;
}
#endif

#if 0
twin_fixed_t
twin_fixed_div (twin_fixed_t a, twin_fixed_t b)
{
    twin_fixed_t q;
    q = (twin_fixed_t) ((((int64_t) a) << 16) / b);
    return q;
}
#endif

twin_fixed_t
twin_fixed_sqrt (twin_fixed_t a)
{
    twin_fixed_t    max, min, mid;
    twin_fixed_t    sqr;

    max = a;
    min = 0;
    while (max > min)
    {
	mid = (max + min) >> 1;
	sqr = twin_fixed_mul (mid, mid);
	if (sqr == a)
	    return mid;
	if (sqr < a)
	    min = mid + 1;
	else
	    max = mid - 1;
    }
    return (max + min) >> 1;
}

twin_sfixed_t
_twin_sfixed_sqrt (twin_sfixed_t as)
{<commit_msg>Fix overflow in twin_fixed_sqrt()<commit_after>/*
 * Twin - A Tiny Window System
 * Copyright © 2004 <NAME> <<EMAIL>>
 * All rights reserved.
 *
 * This Library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Library General Public License as
 * published by the Free Software Foundation; either version 2 of the
 * License, or (at your option) any later version.
 *
 * This Library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Library General Public License for more details.
 *
 * You should have received a copy of the GNU Library General Public
 * License along with the Twin Library; see the file COPYING.  If not,
 * write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
 * Boston, MA 02111-1307, USA.
 */

#include "twinint.h"

#if 0
#include <stdio.h>
#define F(f)	    twin_fixed_to_double(f)
#define DBGMSG(x)   printf x
#else
#define DBGMSG(x)
#endif

#define uint32_lo(i)	((i) & 0xffff)
#define uint32_hi(i)	((i) >> 16)
#define uint32_carry16	((1) << 16)

#if 0
twin_fixed_t
twin_fixed_mul (twin_fixed_t af, twin_fixed_t bf)
{
    uint32_t	    a;
    uint32_t	    b;
    uint16_t	    ah, al, bh, bl;
    uint32_t	    r0, r1, r2, r3;
    uint32_t	    hi, lo;
    twin_fixed_t    r;
    twin_bool_t	    negative = TWIN_FALSE;

    a = (uint32_t) af;
    b = (uint32_t) bf;
    if (af < 0)
    {
	negative = !negative;
	a = -a;
    }
    if (bf < 0)
    {
	negative = !negative;
	b = -b;
    }

    al = uint32_lo (a);
    ah = uint32_hi (a);
    bl = uint32_lo (b);
    bh = uint32_hi (b);

    r0 = (uint32_t) al * bl;
    r1 = (uint32_t) al * bh;
    r2 = (uint32_t) ah * bl;
    r3 = (uint32_t) ah * bh;

    r1 += uint32_hi(r0);    /* no carry possible */
    r1 += r2;		    /* but this can carry */
    if (r1 < r2)	    /* check */
	r3 += uint32_carry16;

    hi = r3 + uint32_hi(r1);
    lo = (uint32_lo (r1) << 16) + uint32_lo (r0);

    DBGMSG (("0x%x * 0x%x = 0x%x%08x\n", a, b, hi, lo));

    r = (twin_fixed_t) ((hi << 16) | (lo >> 16));
    if (negative)
	r = -r;
    DBGMSG (("%9.4f * %9.4f = %9.4f\n", 
	     twin_fixed_to_double(af), twin_fixed_to_double(bf),
	     twin_fixed_to_double (r)));
    return r;
}
#endif

#if 0
twin_fixed_t
twin_fixed_div (twin_fixed_t a, twin_fixed_t b)
{
    twin_fixed_t q;
    q = (twin_fixed_t) ((((int64_t) a) << 16) / b);
    return q;
}
#endif

twin_fixed_t
twin_fixed_sqrt (twin_fixed_t a)
{
    twin_fixed_t    max, min, mid;
    twin_fixed_t    sqr;

    max = a;
    min = 0;
    while (max > min)
    {
	mid = (max + min) >> 1;
	if (mid >= 181*TWIN_FIXED_ONE) {
		max = mid - 1;
		continue;
	}
	sqr = twin_fixed_mul (mid, mid);
	if (sqr == a)
	    return mid;
	if (sqr < a)
	    min = mid + 1;
	else
	    max = mid - 1;
    }
    return (max + min) >> 1;
}

twin_sfixed_t
_twin_sfixed_sqrt (twin_sfixed_t as)
{
{'fraction_non_alphanumeric': 0.12912555290915279, 'fraction_numerical': 0.04321197686287853, 'mean_word_length': 2.640247678018576, 'pattern_counts': {'":': 0, '<': 35, '<?xml version=': 0, '>': 30, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '193918', 'n_tokens_mistral': 2571, 'n_tokens_neox': 2400, 'n_words': 738}