On Wed, 02 Apr 2025 11:16:42 +0000, Farley Flud wrote:
So get going!
I know that all of you astute and enthusiastic GNU/Linux advocates
[snicker, snicker] are just dying for a solution.
This project was only a hobby of mine that stemmed from wanting
to predict my paycheck deductions. The following code is from
2023 but can easily be updated to 2025 by changing the constants.
It is quite accurate in that all returned values agree exactly
with the published manual look-up tables.
Note that it uses the GNU/Linux libdfp decimal FP libraries:
https://github.com/libdfp/libdfp===========================================
Fed W/H C Function
===========================================
// Fed Tax Witholding Function 2023
#define _GNU_SOURCE
#define __STDC_WANT_DEC_FP__
#include <fenv.h>
#include <math.h>
#include <stdio.h>
#include <stdlib.h>
extern _Decimal64 __bid_floatsidd (int i);
// subroutine fed_tax; pass period in per_type = 260, 52, 26, 24, 12, 4, 2
// pre2020, w4_2c = 1 if true, 0 if false
_Decimal64 fed_tax(_Decimal64 gross, int pre2020, int fstat, int fedallow, _Decimal64 fed_add, int per_type, int w4_2c, _Decimal64 w4_3, _Decimal64 w4_4a, _Decimal64 w4_4b, _Decimal64 w4_4c)
{
// These tables should be put in an include file
// Left Tables
// Going down, table-left-1st-column-1... table-left-2nd-column-1...
static _Decimal64 tbll11[8] = { 0.0DD, 14800.0DD, 36800.0DD, 104250.0DD, 205550.0DD, 379000.0DD, 477300.0DD, 708550.0DD};
static _Decimal64 tbll12[8] = { 0.0DD, 0.0DD, 2200.0DD, 10294.0DD, 32580.0DD, 74208.0DD, 105664.0DD, 188601.50DD };
static _Decimal64 tbll13[8] = { 0.0DD, 0.10DD, 0.12DD, 0.22DD, 0.24DD, 0.32DD, 0.35DD, 0.37DD };
static _Decimal64 tbll21[8] = { 0.0DD, 5250.0DD, 16250.0DD, 49975.0DD, 100625.0DD, 187350.0DD, 236500.0DD, 583375.0DD };
static _Decimal64 tbll22[8] = { 0.0DD, 0.0DD, 1100.0DD, 5147.0DD, 16260.0DD, 37104.0DD, 52832.0DD, 174238.25DD };
static _Decimal64 tbll23[8] = { 0.0DD, 0.10DD, 0.12DD, 0.22DD, 0.24DD, 0.32DD, 0.35DD, 0.37DD };
static _Decimal64 tbll31[8] = { 0.0DD, 12200.0DD, 27900.0DD, 72050.0DD, 107550.0DD, 194300.0DD, 243450.0DD, 590300.0DD };
static _Decimal64 tbll32[8] = { 0.0DD, 0.0DD, 1570.0DD, 6868.0DD, 14678.0DD, 35498.0DD, 51226.0DD, 172623.0DD };
static _Decimal64 tbll33[8] = { 0.0DD, 0.10DD, 0.12DD, 0.22DD, 0.24DD, 0.32DD, 0.35DD, 0.37DD };
// Right Tables
static _Decimal64 tblr11[8] = { 0.0DD, 13850.0DD, 24850.0DD, 58575.0DD, 109225.0DD, 195550.0DD, 245100.0DD, 360725.0DD };
static _Decimal64 tblr12[8] = { 0.0DD, 0.0DD, 1100.0DD, 5147.0DD, 16290.0DD, 37104.0DD, 52832.0DD, 93300.75DD};
static _Decimal64 tblr13[8] = { 0.0DD, 0.10DD, 0.12DD, 0.22DD, 0.24DD, 0.32DD, 0.35DD, 0.37DD };
static _Decimal64 tblr21[8] = { 0.0DD, 6925.0DD, 12425.0DD, 29288.0DD, 54613.0DD, 97975.0DD, 122550.0DD, 295988.0DD };
static _Decimal64 tblr22[8] = { 0.0DD, 0.0DD, 550.0DD, 2573.50DD, 8145.0DD, 18552.0DD, 26416.0DD, 87119.13DD };
static _Decimal64 tblr23[8] = { 0.0DD, 0.10DD, 0.12DD, 0.22DD, 0.24DD, 0.32DD, 0.35DD, 0.37DD };
static _Decimal64 tblr31[8] = { 0.0DD, 10400.0DD, 18250.0DD, 40325.0DD, 58075.0DD, 101450.0DD, 126025.0DD, 299450.0DD };
static _Decimal64 tblr32[8] = { 0.0DD, 0.0DD, 785.0DD, 3434.0DD, 7339.0DD, 17749.0DD, 25613.0DD, 86311.75DD };
static _Decimal64 tblr33[8] = { 0.0DD, 0.10DD, 0.12DD, 0.22DD, 0.24DD, 0.32DD, 0.35DD, 0.37DD };
static _Decimal64 stdallow=4300.0DD;
_Decimal64 *p1, *p2, *p3, adj_ann_gross, ann_gross, tentwh, fedwh, tmp1, tmp2;
int index;
// set rounding mode to round half up
fe_dec_setround(FE_DEC_TONEARESTFROMZERO);
//
// Step 1 -- determine adj_ann_gross
//
ann_gross = gross * __bid_floatsidd(per_type);
if (pre2020) {
adj_ann_gross = ann_gross - __bid_floatsidd(fedallow) * stdallow;
if (adj_ann_gross <= 0.0DD) { adj_ann_gross = 0.0DD; }
}
else { // not pre2020
tmp1 = ann_gross + w4_4a;
if (w4_2c) {
tmp2=0.0DD; }
else {
if (fstat==1) {
tmp2=12900.0DD;
}
else { tmp2=8600.0DD; }
}
tmp2=tmp2+w4_4b;
adj_ann_gross = tmp1-tmp2;
if (adj_ann_gross <= 0.0DD) { adj_ann_gross = 0.0DD; }
}
//
//Step 2 -- determine withholding
//
if (pre2020) {
// use left singe/married tables
switch(fstat)
{
case 0:
p1=tbll21; p2=tbll22; p3=tbll23; break;
case 1:
p1=tbll11; p2=tbll12; p3=tbll13; break;
case 2:
p1=tbll21; p2=tbll22; p3=tbll23; break;
}
}
else if ((!pre2020) && (!w4_2c)) {
//use right tables with fstat
switch(fstat)
{
case 0:
p1=tbll21; p2=tbll22; p3=tbll23; break;
case 1:
p1=tbll11; p2=tbll12; p3=tbll13; break;
case 2:
p1=tbll31; p2=tbll32; p3=tbll33; break;
}
}
else if ((!pre2020) && (w4_2c)) {
//use right tables with fstat
switch(fstat)
{
case 0:
p1=tblr21; p2=tblr22; p3=tblr23; break;
case 1:
p1=tblr11; p2=tblr12; p3=tblr13; break;
case 2:
p1=tblr31; p2=tblr32; p3=tblr33; break;
}
}
else {
fprintf(stdout, "\n%s\n", "Error on Table Select");
return 0.0DD;
}
index=0;
while(index<7)
{
if((adj_ann_gross>p1[index]) && (adj_ann_gross<=p1[index+1]))
break;
else
index++;
}
tentwh=(p2[index]+p3[index]*(adj_ann_gross-p1[index]))/__bid_floatsidd(per_type);
tmp1=0.0DD;
if (!pre2020)
{ tmp1 = w4_3/__bid_floatsidd(per_type); }
fedwh = tentwh - tmp1;
if (fedwh<=0.0DD) { fedwh = 0.0DD; }
if (!pre2020)
{ fedwh = fedwh + w4_4c; } //defaults to 0
else { fedwh = fedwh + fed_add;
}
return quantized64(fedwh, 1.00DD);
} // end fed_tax
-- Systemd: solving all the problems that you never knew you had.