github.com/primecitizens/pcz/std@v0.2.1/core/emu64/emu64_386.go (about)

     1  // SPDX-License-Identifier: Apache-2.0
     2  // Copyright 2023 The Prime Citizens
     3  
     4  //go:build 386
     5  
     6  package emu64
     7  
     8  // Floating point control word values.
     9  // Bits 0-5 are bits to disable floating-point exceptions.
    10  // Bits 8-9 are the precision control:
    11  //
    12  //	0 = single precision a.k.a. float32
    13  //	2 = double precision a.k.a. float64
    14  //
    15  // Bits 10-11 are the rounding mode:
    16  //
    17  //	0 = round to nearest (even on a tie)
    18  //	3 = round toward zero
    19  const (
    20  	controlWord64      uint16 = 0x3f + 2<<8 + 0<<10
    21  	controlWord64trunc uint16 = 0x3f + 2<<8 + 3<<10
    22  )
    23  
    24  func Float64ToUint32(float64) uint32
    25  func Uint32ToFloat64(uint32) float64
    26  
    27  //go:noescape
    28  func _mul64by32(lo64 *uint64, a uint64, b uint32) (hi32 uint32)
    29  
    30  //go:noescape
    31  func _div64by32(a uint64, b uint32, r *uint32) (q uint32)
    32  
    33  //go:nosplit
    34  func dodiv(n, d uint64) (q, r uint64) {
    35  	if d > n {
    36  		return 0, n
    37  	}
    38  
    39  	if uint32(d>>32) != 0 {
    40  		t := uint32(n>>32) / uint32(d>>32)
    41  		var lo64 uint64
    42  		hi32 := _mul64by32(&lo64, d, t)
    43  		if hi32 != 0 || lo64 > n {
    44  			return slowdodiv(n, d)
    45  		}
    46  		return uint64(t), n - lo64
    47  	}
    48  
    49  	// d is 32 bit
    50  	var qhi uint32
    51  	if uint32(n>>32) >= uint32(d) {
    52  		if uint32(d) == 0 {
    53  			panicdivide()
    54  		}
    55  		qhi = uint32(n>>32) / uint32(d)
    56  		n -= uint64(uint32(d)*qhi) << 32
    57  	} else {
    58  		qhi = 0
    59  	}
    60  
    61  	var rlo uint32
    62  	qlo := _div64by32(n, uint32(d), &rlo)
    63  	return uint64(qhi)<<32 + uint64(qlo), uint64(rlo)
    64  }