perl XS

h2xs -A FloatCalc

然后改写FloatCalc.xs,以下提供3种有别于标准写法的方式。

方式一:

#define PERL_NO_GET_CONTEXT
#include "EXTERN.h"
#include "perl.h"
#include "XSUB.h"
#include <stdio.h>

XS(XS_FloatCalc_pow)
{
    dXSARGS;
    if (items != 2)
       croak("usage:FloatCalc::pow(x,y)");
    {
		double	RETVAL;
		dXSTARG;
		RETVAL = pow(SvNV(ST(0)),SvNV(ST(1)) );
		XSprePUSH; 
		PUSHn(RETVAL);
    }
    XSRETURN(1);
}

XS(boot_FloatCalc)
{
    dXSARGS;
    const char* file = __FILE__;
	newXS("FloatCalc::pow", XS_FloatCalc_pow, file);

	if (PL_unitcheckav)
		call_list(PL_scopestack_ix, PL_unitcheckav);
    XSRETURN_YES;
}


方式二:

#define PERL_NO_GET_CONTEXT
#include "EXTERN.h"
#include "perl.h"
#include "XSUB.h"
#include <stdio.h>

XS(XS_FloatCalc_pow)
{
    dXSARGS;
    if (items != 2)
       croak("usage:FloatCalc::pow(x,y)");
    {
		double result;
		sp = mark;
		result = pow(SvNV(ST(0)), SvNV(ST(1)) );
		XPUSHs(sv_2mortal(newSVnv(result)));
    }
    XSRETURN(1);
}

XS(boot_FloatCalc)
{
    dXSARGS;
    const char* file = __FILE__;
	newXS("FloatCalc::pow", XS_FloatCalc_pow, file);

	if (PL_unitcheckav)
		call_list(PL_scopestack_ix, PL_unitcheckav);
    XSRETURN_YES;
}


方式三:

#define PERL_NO_GET_CONTEXT
#include "EXTERN.h"
#include "perl.h"
#include "XSUB.h"
#include <stdio.h>


XS(XS_FloatCalc_pow)
{
    dSP; 			//得到sp
    dAXMARK; 		//得到mark
    dITEMS;			//得到items = sp - mark
    if (items != 2)
       croak("usage:FloatCalc::pow(x,y)");
    {
		double result;
		sp = mark;	//回到起始位置
		result = pow(SvNV(ST(0)), SvNV(ST(1)) );
		XPUSHs(sv_2mortal(newSVnv(result)));
    }
    PL_stack_sp = sp;	//返回栈帧
	return;	
}

XS(boot_FloatCalc)
{
    dXSARGS;
    const char* file = __FILE__;
	newXS("FloatCalc::pow", XS_FloatCalc_pow, file);

	if (PL_unitcheckav)
		call_list(PL_scopestack_ix, PL_unitcheckav);
    XSRETURN_YES;
}

方式四:

#define PERL_NO_GET_CONTEXT
#include "EXTERN.h"
#include "perl.h"
#include "XSUB.h"
#include <stdio.h>

XS(XS_FloatCalc_pow)
{
    dXSARGS;
    double result;
    if (items != 2)
    {
       croak("usage:FloatCalc::pow(x,y)");
       XSRETURN_EMPTY;
    }
    result = pow(SvNV(ST(0)),SvNV(ST(1)) );
    XSRETURN_NV(result);
}

XS(boot_FloatCalc)
{
    I32 ax = POPMARK;		//仅需要ax
    const char* file = __FILE__;
    newXS("FloatCalc::pow", XS_FloatCalc_pow, file);

    if (PL_unitcheckav)
        call_list(PL_scopestack_ix, PL_unitcheckav);
    XSRETURN_YES;
}

 方式五:

#define PERL_NO_GET_CONTEXT
#include "EXTERN.h"
#include "perl.h"
#include "XSUB.h"
#include <stdio.h>

XS(XS_FloatCalc_pow)
{
    SV **mark = PL_stack_base + (*PL_markstack_ptr--);
    int items = PL_stack_sp - mark;
    double	result;
    if (items != 2)
    {
       croak("usage:FloatCalc::pow(x,y)");
       PL_stack_sp = mark;
       return;
    }
	result = pow(SvNV(mark[1+0]),SvNV(mark[1+1]) );
	mark[1+0] = sv_2mortal(newSVnv(result));
	PL_stack_sp = mark +1;
	return;
}

XS(boot_FloatCalc)
{
    I32 ax = POPMARK;		//仅需要ax
    const char* file = __FILE__;
	newXS("FloatCalc::pow", XS_FloatCalc_pow, file);

	if (PL_unitcheckav)
		call_list(PL_scopestack_ix, PL_unitcheckav);
    XSRETURN_YES;
}


 

测试:

#!/usr/bin/perl
use FloatCalc;
my $result = pow(2.0,4.0);
print "pow(2.0,4.0) = $result\n";

my $result = pow(2.0);  # 会有用法提示

<>;

结果:

C:\Users\G-Spider\FloatCalc>test.pl
pow(2.0,4.0) = 16
usage:FloatCalc::pow(x,y) at C:\Users\G-Spider\Desktop\hello.pl line 6.




 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值