o
    8Va2/                     @   s  d dl mZmZmZ d dlmZ d dlmZmZm	Z	 d dl
Z
d dlZd dlZd dlZi Zded< ded< ed ed	< i Zd
ed< ed ed	< ded< i Zg ded< g ded< g ded< g ded< g dZdd Zd0ddZdd Zdd Zg Zg ZeD ]\ZZee Zeeereeef qeeef qdd Zd d! Zd"d# Zd$d% Zd&d' Z d(d) Z!d*d+ Z"d,d- Z#d.d/ Z$dS )1    )xyz)skip)codegenmake_routineget_code_generatorNzy
program main
  include "codegen.h"
  integer :: result;
  result = 0

  %(statements)s

  call exit(result)
end program
F95z
#include "codegen.h"
#include <stdio.h>
#include <math.h>

int main() {
  int result = 0;

  %(statements)s

  return result;
}
C89C99z
  if (fabs(%(call)s)>%(threshold)s) {
    printf("Numerical validation failed: %(call)s=%%e threshold=%(threshold)s\n", %(call)s);
    result = -1;
  }
z
  if (abs(%(call)s)>%(threshold)s) then
    write(6,"('Numerical validation failed:')")
    write(6,"('%(call)s=',e15.5,'threshold=',e15.5)") %(call)s, %(threshold)s
    result = -1;
  end if
)zcc -c codegen.c -o codegen.ozcc -c main.c -o main.oz#cc main.o codegen.o -lm -o test.execc)z$gfortran -c codegen.f90 -o codegen.oz6gfortran -ffree-line-length-none -c main.f90 -o main.oz%gfortran main.o codegen.o -o test.exegfortran)zg95 -c codegen.f90 -o codegen.oz1g95 -ffree-line-length-huge -c main.f90 -o main.oz g95 main.o codegen.o -o test.exeg95)z!ifort -c codegen.f90 -o codegen.ozifort -c main.f90 -o main.oz"ifort main.o codegen.o -o test.exeifort)r
   r   r   r   r	   r   r	   r   r	   r   c                 C   s<   t tjd}| D ]}tj||dtjd}|dkr dS qdS )z>Run a series of commands and only return True if all ran fine.wT)stdoutshellstderrr   F)openosdevnull
subprocesscallZSTDOUT)commandsZnullZcommandZretcode r   C/usr/lib/python3/dist-packages/sympy/external/tests/test_codegen.pytry_runt   s   
r!   Tc                 C   s^  |  }|tv s
J |tv sJ tdd }|dvr tdtd| d|  }t	 }t
| |r>t||ddd	 nt|d}	|	j|ddd	 g }
|D ]/\}}}}d
|ddd |D |f }|dkrrt|}tt|}|
t| ||d  qO|dkrd}n|drd}ntd| t|d}|t| dd|
i  W d   n1 sw   Y  t|}|rtdg}nd}|dks|dkr|r|rdd }|d |d |d |d  |d |d |d! |d" t
| t| ntd#| tjd$ t
| |sJ d%|d&|f |s-J d'|d&|f dS )(a|  A driver for the codegen tests.

       This driver assumes that a compiler ifort is present in the PATH and that
       ifort is (at least) a Fortran 90 compiler. The generated code is written in
       a temporary directory, together with a main program that validates the
       generated code. The test passes when the compilation and the validation
       run correctly.
    ZSYMPY_TEST_CLEAN_TEMPalways)r"   successneverzSSYMPY_TEST_CLEAN_TEMP must be one of the following: 'always', 'success' or 'never'.z_sympy_%s_testz%s_r   T)Zto_filesz%s(%s)-(%s),c                 s   s    | ]}t |V  qd S N)str).0argr   r   r    	<genexpr>   s    zrun_test.<locals>.<genexpr>r	   )r   	thresholdzmain.f90Czmain.cz2FIXME: filename extension unknown for language: %sr   Z
statements Nz
./test.exeFr#   c                 S   s   t j| rt |  d S d S r&   )r   pathisfileremove)filenamer   r   r    safe_remove   s   zrun_test.<locals>.safe_removezcodegen.f90z	codegen.cz	codegen.hz	codegen.ozmain.oztest.exezTEST NOT REMOVED: %s)filez"failed to compile %s code with:
%s
z"failed to execute %s code from:
%s)uppermain_templatenumerical_test_templater   getenvlower
ValueErrortempfileZmkdtempgetcwdchdirr   r   writejoinfortranize_double_constantsr'   append
startswithNotImplementedErrorr   r!   rmdirprintsysr   )ZlabelZroutinesnumerical_testslanguager   friendlyZcleanZworkZoldworkZcode_genZtest_stringsZfn_nameargsexpectedr+   Zcall_stringZf_namefZcompiledZexecutedr2   r   r   r    run_test   sz   









rM   c                    sL   ddl   d} d} fdd}dd }||| } ||| } | S )	z;
    Replaces every literal float with literal doubles
    r   Nz\d+(\.)?\d*[eE]-?\d+z\d+\.\d*(?!\d*d)c                    s     dd| dS )Nz[eE]dr   )subgroupZmatchobjrer   r    subs_exp   s   z-fortranize_double_constants.<locals>.subs_expc                 S   s   d|  d S )Nz%sd0r   )rP   rQ   r   r   r    
subs_float   s   z/fortranize_double_constants.<locals>.subs_float)rS   compilerO   )Zcode_stringZpattern_expZpattern_floatrT   rU   r   rR   r    r@      s   

r@   c                 C   sD   t dt}ddg}ztd|g|| |dd W dS  ty!   Y dS w )Ntest)rW   )      ?rX   V瞯<)rW   )      rZ   rY   is_feasibleF)rI   T)r   r   rM   AssertionError)rH   r   ZroutinerG   r   r   r    r[      s   
r[   c                   C      dt v r
td d S d S )Nr   z*`cc' command didn't work as expected (C89)invalid_lang_compilersr   r   r   r   r    test_C89_cc     r`   c                   C   r]   )Nr   z*`cc' command didn't work as expected (C99)r^   r   r   r   r    test_C99_cc  ra   rb   c                   C   r]   )Nr   z'`ifort' command didn't work as expectedr^   r   r   r   r    test_F95_ifort  ra   rc   c                   C   r]   )Nr   z*`gfortran' command didn't work as expectedr^   r   r   r   r    test_F95_gfortran  ra   rd   c                   C   r]   )Nr   z%`g95' command didn't work as expectedr^   r   r   r   r    test_F95_g95   ra   re   c                  C   s<   ddg} dt t t fg}tD ]\}}td|| || qd S )N)rW   )rX   g      @g      @g      5@rY   )rW   )rZ   g       @      rf   rY   rW   Zbasic_codegen)r   r   r   valid_lang_commandsrM   )rG   	name_exprlangr   r   r   r    test_basic_codegen'  s   rj   c                  C   sX  ddl m} m}m}m}m}m}m}m}m	}m
}	m}
m}m}m}m} dttfd| tfd|tfd|tfd|tfd|tfd	|tfd
|tfd|	tfd|
tfd|tfd|tfd|tfg}g }|D ]\}}dD ]}||t|}|||f|df qoqitD ]"\}}|drd|tfd|tfg}ng }td|| ||| qd S )Nr   )acosasinatanceilingcoscoshfloorloglnsinsinhsqrttantanhNZ	test_fabsZ	test_acosZ	test_asinZ	test_atanZtest_cosZ	test_coshZtest_logZtest_lnZtest_sinZ	test_sinhZ	test_sqrtZtest_tanZ	test_tanh)皙?      ?皙?+=r,   Z
test_floorZ	test_ceilZintrinsic_math1)sympyrk   rl   rm   rn   ro   rp   rq   rr   rs   rt   ru   rv   rw   rx   ry   absr   subsrA   rg   rB   rM   )rk   rl   rm   rn   ro   rp   rq   rr   rs   rt   ru   rv   rw   rx   ry   rh   rG   nameexprxvalrK   ri   r   Zname_expr_Cr   r   r    test_intrinsic_math1_codegen1  s:   D














r   c                  C   s   ddl m} m} d| ttfdtt fg}g }|D ]"\}}dD ]\}}||t|t|}||||f|df qqtD ]\}	}
td|||	|
 q>d S )Nr   )atan2ry   Z
test_atan2Ztest_pow))rz   ?)r{   皙ɿ)r|   r|   r}   Zintrinsic_math2)	r~   r   ry   r   r   r   rA   rg   rM   )r   ry   rh   rG   r   r   r   yvalrK   ri   r   r   r   r    test_instrinsic_math2_codegenR  s   
r   c                  C   s   ddl m} m}m}m} d| t|t |t d  fd||||||||tt t fg}g }|D ](\}}dD ]!\}}	}
||	t|	t|		t|
}|
|||	|
f|df q@q:tD ]\}}td|||| qed S )	Nr   )rt   ro   rw   ry   Ztest1   Ztest2))rz   r   g333333ӿ)r{   r   g        )r|   g @r|   g-q=Zcomplicated_codegen)r~   rt   ro   rw   ry   r   r   r   expandr   rA   rg   rM   )rt   ro   rw   ry   rh   rG   r   r   r   r   ZzvalrK   ri   r   r   r   r    test_complicated_codegenb  s   ". 
r   )T)%Z	sympy.abcr   r   r   Zsympy.testing.pytestr   Zsympy.utilities.codegenr   r   r   rF   r   r;   r   r6   r7   Zcompile_commandsZcombinations_lang_compilerr!   rM   r@   r[   rg   r_   ri   Zcompilerr   rA   r`   rb   rc   rd   re   rj   r   r   r   r   r   r   r    <module>   sR   		
`

!