
# To install, you have to specify a C++ compiler and optionally
# a C compiler, along with some compile-time options.

CPP = g++
# A C++ compiler.

CC = gcc
# A C or C++ compiler.
# There are a few components written in C which may be compiled
# under C++, but C compilers tend to generate slightly better code.
# The C++ and C compilers (if different) must generate
# compatible code.

CFLAGS = -O2 
# Flags for the C compiler

CPPFLAGS =  $(CFLAGS)
# Flags for the C++ compiler (usually the same)

# Useful compile-time options (CFLAGS):
# -O2 -g -mv8 -qarch=ppc 
# -DAVOID_FLOAT -DTBL_REM -DAVOID_BRANCHING -DFFT_PIPELINE 
# -DRANGE_CHECK -DCPLUSPLUS_ONLY -DSINGLE_MUL -DFAST_INT_MUL 
# (CPPFLAGS only):
# -+
 
# -O2 
#   This turns on the optimizer, which is essential for
#   reasonable performance. 
 
# -g
#   You need this if you want to run a debugger, like gdb.
#   Caution: with some compilers (but not GNU's), this will
#   turn off optimization (sometimes without warning).

# -mv8
#   On SPARC-10s and later, make sure you include this flag.
#   This enables the use of fast integer multiplication.
#   On earlier SPARC stations, you should NOT use this flag,
#   but you should seriously consider setting -DSINGLE_MUL (see below).

# -qarch=ppc
#   On PowerPCs, this is needed with the AIX compiler to get
#   access to the full instruction set.

# -+
#   Add this to the CPPFLAGS line when using the AIX compiler xlC.

# -DAVOID_FLOAT
#   On machines with fast integer multiplication, but slow
#   floating point, this flag lead to faster code.
#   PowerPCs are faster with this option.

# -DTBL_REM
#   With this flag, some divisions are avoided in the
#   ZZ_pX multiplication routines.  If you use the -DAVOID_FLOAT flag,
#   then you should probably use this one too.

# -DAVOID_BRANCHING
#   With this option, branches are replaced at several 
#   key points with equivalent code using shifts and masks.
#   Recommended for use with RISC architectures, especially
#   ones with deep pipelines and high branch penalities.

# -DFFT_PIPELINE
#   If using -DAVOID_BRANCHING, you might want to try this as well.
#   This causes the FFT routine to use a software pipeline.
 
# -DRANGE_CHECK
#   This will generate vector subscript range-check code.

# -DCPLUSPLUS_ONLY
#   It is possible to compile everything using C++ only.
#   If you want to do this, make CC and CPP the same.
#   You may also want to set this flag, which eliminates some
#   "C" linkage that is no longer necessary.

# -DSINGLE_MUL
#   On platforms that support it, you can use the SINGLE_MUL option,
#   which uses a 26-bit radix.  On machines with fast floating point,
#   but slow integer multiplications, this will generally yield
#   faster code.
#   With this option, integer multiplications are avoided entirely.
#   Only floating point multiplies are used.
#   Some old SPARC stations perform better with this flag.
 
# -DFAST_INT_MUL
#   This is a bit esoteric.  If using SINGLE_MUL, and your machine
#   has a fast integer multiply instruction, this might yield
#   faster code.  Experiment!




OBJ1 = ZZ.o ZZ_p.o ZZ_pX.o ZZ_pX1.o tools.o vec_ZZ.o vec_ZZ_p.o vec_long.o 
OBJ2 = FFT.o lip.o ZZVec.o vec_ZZVec.o pair_ZZ_pX_long.o GetTime.o
OBJ3 = ZZ_pXFactoring.o  fileio.o vec_vec_ZZ.o mat_ZZ.o mat_ZZ_p.o mat_zz_p.o
OBJ4 = LLL.o FacVec.o vec_vec_long.o vec_vec_ZZ_p.o ZZ_pXCharPoly.o zz_pXCharPoly.o ZZXCharPoly.o
OBJ5 = zz_p.o vec_zz_p.o vec_vec_zz_p.o zz_pX.o zz_pX1.o pair_zz_pX_long.o zz_pXFactoring.o
OBJ6 = ZZX.o pair_ZZX_long.o ZZXFactoring.o HNF.o mat_poly_ZZ_p.o mat_poly_zz_p.o mat_poly_ZZ.o
OBJ7 = xdouble.o LLL_XD.o RR.o vec_RR.o vec_vec_RR.o mat_RR.o LLL_RR.o IsFinite.o

# C files
SRC0 = lip.c MakeDesc.c MakeDescAux.c GetTime1.c GetTime2.c GetTime3.c GetTime4.c GetTime5.c IsFinite.c

# C++ files
SRC1 = ZZ.c ZZ_p.c ZZ_pX.c ZZ_pX1.c tools.c vec_ZZ.c vec_ZZ_p.c vec_long.c 
SRC2 = FFT.c ZZVec.c vec_ZZVec.c pair_ZZ_pX_long.c 
SRC3 = ZZ_pXFactoring.c  fileio.c  vec_vec_ZZ.c mat_ZZ.c mat_ZZ_p.c mat_zz_p.c
SRC4 = LLL.c FacVec.c vec_vec_long.c vec_vec_ZZ_p.c ZZ_pXCharPoly.c zz_pXCharPoly.c ZZXCharPoly.c
SRC5 = zz_p.c vec_zz_p.c vec_vec_zz_p.c zz_pX.c zz_pX1.c pair_zz_pX_long.c zz_pXFactoring.c
SRC6 = ZZX.c pair_ZZX_long.c ZZXFactoring.c HNF.c mat_poly_ZZ_p.c mat_poly_zz_p.c mat_poly_ZZ.c

SRC7 = ZZ.h ZZ_p.h ZZ_pX.h tools.h vec_ZZ.h vec_ZZ_p.h vec_long.h 
SRC8 = FFT.h lip.h  IsFinite.h ZZVec.h vec_ZZVec.h pair_ZZ_pX_long.h PrimeSource.h
SRC9 = ZZ_pXFactoring.h  fileio.h  vec_vec_ZZ.h mat_ZZ.h mat_ZZ_p.h mat_zz_p.h
SRC10 = LLL.h FacVec.h vec_vec_long.h vec_vec_ZZ_p.h
SRC11 = zz_p.h vec_zz_p.h vec_vec_zz_p.h zz_pX.h pair_zz_pX_long.h zz_pXFactoring.h
SRC12 = ZZX.h pair_ZZX_long.h ZZXFactoring.h vector.h matrix.h pair.h HNF.h mat_poly_ZZ_p.h mat_poly_zz_p.h mat_poly_ZZ.h

SRC13 = Test.c BerlekampTest.c CanZassTest.c ZZXFacTest.c LLLTest.c
SRC14 = MatrixTest.c CharPolyTest.c RRTest.c TestGetTime.c
SRC15 = xdouble.c xdouble.h LLL_XD.c RR.c RR.h vec_RR.c vec_RR.h
SRC16 = vec_vec_RR.c vec_vec_RR.h mat_RR.c mat_RR.h LLL_RR.c

# sh script
SRC17 = MakeGetTime TestScript


SRCx1 = $(SRC0) $(SRC1) $(SRC2) $(SRC3) $(SRC4) $(SRC5) $(SRC6) $(SRC7) $(SRC8)
SRCx2 = $(SRC9) $(SRC10) $(SRC11) $(SRC12) $(SRC13) $(SRC14) $(SRC15) $(SRC16) $(SRC17)

TESTFILES1 = test.64 test.128 test.256 sptest.64 sptest.128 sptest.256
TESTFILES2 = p.1024b p.128b  p.2048b p.256b  p.25b   p.32b   p.512b  p.64b
TESTFILES3 = BerlekampTestIn BerlekampTestOut CanZassTestIn CanZassTestOut
TESTFILES4 = ZZXFacTestIn ZZXFacTestOut LLLTestIn LLLTestOut RRTestIn RRTestOut
TESTFILES5 = MatrixTestIn MatrixTestOut CharPolyTestIn CharPolyTestOut 
TESTFILES = $(TESTFILES1) $(TESTFILES2) $(TESTFILES3) $(TESTFILES4) $(TESTFILES5)

DOC1 = ZZ.txt ZZ_p.txt ZZ_pX.txt vec_ZZ_p.txt zz_p.txt zz_pX.txt vec_zz_p.txt
DOC2 = ZZ_pXFactoring.txt zz_pXFactoring.txt ZZX.txt ZZXFactoring.txt
DOC3 = vector.txt matrix.txt vec_ZZ.txt mat_ZZ.txt ZZVec.txt LLL.txt
DOC4 = tools.txt mat_ZZ_p.txt mat_zz_p.txt HNF.txt mat_poly_ZZ_p.txt mat_poly_zz_p.txt mat_poly_ZZ.txt
DOC5 = xdouble.txt RR.txt vec_RR.txt mat_RR.txt

DOC = $(DOC1) $(DOC2) $(DOC3) $(DOC4)  $(DOC5)

SRC= $(SRCx1) $(SRCx2) 

OBJ = $(OBJ1) $(OBJ2) $(OBJ3) $(OBJ4) $(OBJ5) $(OBJ6) $(OBJ7)

PROGS = Test BerlekampTest CanZassTest ZZXFacTest LLLTest MatrixTest CharPolyTest RRTest

install:
	make mach_desc.h
	make ntl.a
	make Test
	./Test
	sh TestScript

ntl.tar: 
	tar -cvf ntl.tar README makefile m1 m2 m3 m4 $(SRC) $(DOC) $(TESTFILES)

ntl.a:	$(OBJ) 
	ar ruv ntl.a $(OBJ)
	- ranlib ntl.a

mach_desc.h: 
	$(CC) -c $(CFLAGS) MakeDescAux.c
	$(CC) -o MakeDesc $(CFLAGS) MakeDesc.c MakeDescAux.o
	./MakeDesc


clobber:	
	- rm ntl.a mach_desc.h MakeDesc GetTime.c TestGetTime 
	- rm $(PROGS)
	- rm *.o

clean:
	- rm *.o 
	- rm MakeDesc TestGetTime

lip.o:	lip.c mach_desc.h
	$(CC) $(CFLAGS) -c lip.c

IsFinite.o:	IsFinite.c
	$(CC) $(CFLAGS) -c IsFinite.c

GetTime.c:
	sh MakeGetTime $(CC) $(CFLAGS)

GetTime.o: GetTime.c 
	$(CC) $(CFLAGS) -c GetTime.c


.c.o: 
	$(CPP) $(CPPFLAGS) -c $<

.c: 
	$(CPP) $(CPPFLAGS) -o $@ $< ntl.a  -lm

