# Copyright (C) 2001-2010, Parrot Foundation.
# $Id: root.in 48548 2010-08-17 12:09:53Z petdance $

###############################################################################
#
# NOTE:
#
# This makefile makes use of specific .dummy targets (rather than .PHONY
# or .VIRTUAL targets) in an effort to work with various flavors of make.
#
###############################################################################

###############################################################################
#
# INSTALL CONFIGURATIONS:
#
###############################################################################

DEVEL           = @DEVEL@
VERSION         = @VERSION@$(DEVEL)
SOVERSION       = @VERSION@

CONFIG_ARGS     = @configure_args@

# Override at least PREFIX with the install location if you're going
# to be using this outside of your build area.
BUILDPREFIX     =
PREFIX          = @prefix@
EXEC_PREFIX     = @exec_prefix@
DESTDIR         =
BIN_DIR         = @bindir@
LIB_DIR         = @libdir@
INCLUDE_DIR     = @includedir@
DATA_DIR        = @datadir@
DOC_DIR         = @docdir@
VERSION_DIR     = @versiondir@


###############################################################################
#
# SOURCE CONFIGURATIONS:
#
# Set up information about directories where the sources can be found.
#
###############################################################################

# where we're building parrot from (needed for pbc_to_exe)
BUILD_DIR = @build_dir@

# directory for build tools
BUILD_TOOLS_DIR = tools/build

# directory for header files
INC_DIR         = @inc@

# directory with Parrot modules
LIBRARY_DIR     = runtime/parrot/library

###############################################################################
#
# BUILD TOOL CONFIGURATIONS:
#
# DO NOT ADD C COMPILER FLAGS HERE
# Add them in Configure.pl--look for the
# comment 'ADD C COMPILER FLAGS HERE'
#
###############################################################################

PERL             = @perl@
CP               = @cp@
MV               = @mv@
CHMOD            = @chmod@
MKPATH           = @mkpath@
RM_F             = @rm_f@
RM_RF            = @rm_rf@
TOUCH            = @touch@
AR_CR            = @ar@ @ar_flags@
RANLIB           = @ranlib@
YACC             = @yacc@
LEX              = @lex@
AS               = @as@
CC               = @cc@
CC_INC           = @cc_inc@
C_LIBS           = @libs@
CC_SHARED        = @cc_shared@
CC_O_OUT         = @cc_o_out@
CC_WARN          = @ccwarn@
CFLAGS           = $(CC_INC) @ccflags@ @cc_build_call_frames@ @cc_debug@ @gc_flag@ @clock_best@ $(CC_SHARED)
LINK_DYNAMIC     = @link_dynamic@
LINK             = @link@
LINKFLAGS        = @linkflags@ @link_debug@ @ld_debug@
LD               = @ld@
LD_OUT           = @ld_out@
LDFLAGS          = @ldflags@ @ld_debug@
INNO_SETUP       = iscc
TEMPDIR          = @tempdir@
RPATH_BLIB       = @rpath_blib@
#IF(darwin):export MACOSX_DEPLOYMENT_TARGET = @osx_version@

###############################################################################
#
# file extensions and util flags
#
###############################################################################

O                = @o@
EXE              = @exe@
SHARE_EXT        = @share_ext@
LOAD_EXT         = @load_ext@
A                = @a@
LD_SHARE_FLAGS   = @ld_share_flags@
LD_LOAD_FLAGS    = @ld_load_flags@
LINKARGS         = $(LDFLAGS) $(LD_LOAD_FLAGS) @libparrot_ldflags@ @icu_shared@ @libs@

# generated by config/init/headers.pm
NONGEN_HEADERS   = @TEMP_nongen_headers@

# The headerizer
HEADERIZER       = $(PERL) $(BUILD_TOOLS_DIR)/headerizer.pl

include src/dynpmc/Defines.mak
include src/dynoplibs/Defines.mak
include compilers/imcc/Defines.mak
include compilers/pirc/Defines.mak
include compilers/tge/Defines.mak
include compilers/pge/Defines.mak
include compilers/pct/Defines.mak
include compilers/opsc/Defines.mak
include ext/nqp-rx/Defines.mak
include compilers/data_json/Defines.mak

###############################################################################
#
# CONFIGURE_GENERATED_FILES:
#
# These files are created when Configure.pl runs.
#
# We don't delete these on 'clean'; only on 'realclean'.
# That way, we don't have to re-Configure.pl after making
# clean.
#
###############################################################################

GEN_MAKEFILES = \
    Makefile \
    docs/Makefile \
    editor/Makefile \
    ext/Makefile \
    src/dynoplibs/Rules.mak \
    src/dynoplibs/Defines.mak \
    src/dynpmc/Rules.mak \
    src/dynpmc/Defines.mak \
    compilers/imcc/Rules.mak

GEN_CONFIGS = \
    $(INC_DIR)/config.h \
    $(INC_DIR)/platform.h \
    $(INC_DIR)/platform_limits.h \
    $(INC_DIR)/has_header.h \
    $(INC_DIR)/feature.h \
    $(INC_DIR)/core_pmcs.h \
    src/exec_dep.c \
    src/exec_dep.h \
    lib/Parrot/Config/Generated.pm \
    lib/Parrot/PMC.pm \
    runtime/parrot/include/config.fpmc \
    $(LIBRARY_DIR)/config.pir \
    src/platform.c \
#IF(platform_asm):    src/platform_asm.s \
#IF(has_opengl):    src/glut_nci_thunks.nci \
#IF(has_glut):    src/glut_callbacks.c \
    src/core_pmcs.c \
    config_lib.pir \
    parrot.pc \
    compilers/imcc/imcc.y.flag \
    compilers/imcc/imcc.l.flag

GEN_PASM_INCLUDES = \
	runtime/parrot/include/cclass.pasm \
	runtime/parrot/include/datatypes.pasm \
	runtime/parrot/include/iterator.pasm \
	runtime/parrot/include/call_bits.pasm \
	runtime/parrot/include/timer.pasm \
	runtime/parrot/include/except_types.pasm \
	runtime/parrot/include/except_severity.pasm \
	runtime/parrot/include/hash_key_type.pasm \
	runtime/parrot/include/interpflags.pasm \
	runtime/parrot/include/interpdebug.pasm \
	runtime/parrot/include/interptrace.pasm \
	runtime/parrot/include/interpcores.pasm \
	runtime/parrot/include/cloneflags.pasm \
	runtime/parrot/include/iglobals.pasm \
	runtime/parrot/include/sysinfo.pasm \
	runtime/parrot/include/stdio.pasm \
	runtime/parrot/include/socket.pasm \
	runtime/parrot/include/libpaths.pasm \
	runtime/parrot/include/dlopenflags.pasm \
	runtime/parrot/include/longopt.pasm \
	runtime/parrot/include/packfile_segments.pasm \
	runtime/parrot/include/packfile_constants.pasm \
	runtime/parrot/include/packfile_annotation_key_type.pasm \
	runtime/parrot/include/stat.pasm \
	runtime/parrot/include/stringinfo.pasm \
	runtime/parrot/include/warnings.pasm \
	runtime/parrot/include/errors.pasm \
	runtime/parrot/include/interpinfo.pasm \
	runtime/parrot/include/tm.pasm \
	runtime/parrot/include/pmctypes.pasm \

GEN_PM_INCLUDES = \
	lib/Parrot/Pmc2c/PCCMETHOD_BITS.pm

CONFIGURE_GENERATED_FILES = \
    $(GEN_CONFIGS) \
    $(GEN_MAKEFILES) \
    ext/Parrot-Embed/Makefile.PL \
    myconfig  \
    MANIFEST.configure.generated \
    .configure_trace.sto \
    .parrot_current_rev \
#IF(has_opengl):    runtime/parrot/include/opengl_defines.pasm \
#IF(has_opengl):    runtime/parrot/library/OpenGL_funcs.pir \
    runtime/parrot/include/signal.pasm


###############################################################################
#
# "FLUID" GENERATED FILES:
#
# These files are created during the build process.
#
# We *do* delete these on 'clean'.
#
###############################################################################

GEN_HEADERS = \
    $(INC_DIR)/vtable.h \
    $(INC_DIR)/extend_vtable.h \
    $(INC_DIR)/pbcversion.h

GEN_SOURCES = \
    src/nci.c \
    src/glut_nci_thunks.c \
    src/parrot_config.c \
    src/null_config.c \
    src/install_config.c \
    src/extend_vtable.c \
    src/extra_nci_thunks.c

GEN_MODULES = \

GEN_LIBRARY = \
    $(LIBRARY_DIR)/Archive/Tar.pbc \
    $(LIBRARY_DIR)/Archive/Zip.pbc \
    $(LIBRARY_DIR)/CGI/QueryHash.pbc \
    $(LIBRARY_DIR)/Crow.pbc \
    $(LIBRARY_DIR)/config.pbc \
    $(LIBRARY_DIR)/Configure/genfile.pbc \
    $(LIBRARY_DIR)/Config/JSON.pbc \
    $(LIBRARY_DIR)/Data/Dumper/Base.pbc \
    $(LIBRARY_DIR)/Data/Dumper/Default.pbc \
    $(LIBRARY_DIR)/Data/Dumper.pbc \
    $(LIBRARY_DIR)/Digest/MD5.pbc \
    $(LIBRARY_DIR)/distutils.pbc \
    $(LIBRARY_DIR)/dumper.pbc \
    $(LIBRARY_DIR)/yaml_dumper.pbc \
    $(LIBRARY_DIR)/Getopt/Obj.pbc \
    $(LIBRARY_DIR)/HTTP/Message.pbc \
    $(LIBRARY_DIR)/Iter.pbc \
    $(LIBRARY_DIR)/JSON.pbc \
    $(LIBRARY_DIR)/LWP/Protocol.pbc \
    $(LIBRARY_DIR)/LWP/UserAgent.pbc \
    $(LIBRARY_DIR)/Math/Rand.pbc \
    $(LIBRARY_DIR)/MIME/Base64.pbc \
    $(LIBRARY_DIR)/NCI/Utils.pbc \
    $(LIBRARY_DIR)/NCI/call_toolkit_init.pbc \
    $(LIBRARY_DIR)/ncurses.pbc \
#IF(has_opengl):    $(LIBRARY_DIR)/OpenGL.pbc \
#IF(has_opengl):    $(LIBRARY_DIR)/OpenGL_funcs.pbc \
#IF(has_opengl):    $(LIBRARY_DIR)/OpenGL/Math.pbc \
    $(LIBRARY_DIR)/osutils.pbc \
    $(LIBRARY_DIR)/P6object.pbc \
    $(LIBRARY_DIR)/ProfTest.pbc \
    $(LIBRARY_DIR)/ProfTest/PIRProfile.pir \
    $(LIBRARY_DIR)/ProfTest/NQPProfile.pir \
    $(LIBRARY_DIR)/ProfTest/Matcher.pir \
    $(LIBRARY_DIR)/ProfTest/Want.pir \
    $(LIBRARY_DIR)/parrotlib.pbc \
    $(LIBRARY_DIR)/pcore.pbc \
    $(LIBRARY_DIR)/pcre.pbc \
    $(LIBRARY_DIR)/Parrot/Coroutine.pbc \
    $(LIBRARY_DIR)/Parrot/Exception.pbc \
    $(LIBRARY_DIR)/PGE/Dumper.pbc \
    $(LIBRARY_DIR)/PGE/Glob.pbc \
    $(LIBRARY_DIR)/PGE/Perl6Grammar.pbc \
    $(LIBRARY_DIR)/PGE/Text.pbc \
    $(LIBRARY_DIR)/PGE/Util.pbc \
    $(LIBRARY_DIR)/Protoobject.pbc \
    $(LIBRARY_DIR)/Range.pbc \
    $(LIBRARY_DIR)/Stream/Base.pbc \
    $(LIBRARY_DIR)/Stream/Combiner.pbc \
    $(LIBRARY_DIR)/Stream/Coroutine.pbc \
    $(LIBRARY_DIR)/Stream/Filter.pbc \
    $(LIBRARY_DIR)/Stream/Lines.pbc \
    $(LIBRARY_DIR)/Stream/ParrotIO.pbc \
    $(LIBRARY_DIR)/Stream/Replay.pbc \
    $(LIBRARY_DIR)/Stream/Sub.pbc \
    $(LIBRARY_DIR)/Stream/Writer.pbc \
    $(LIBRARY_DIR)/String/Utils.pbc \
    $(LIBRARY_DIR)/TAP/Formatter.pbc \
    $(LIBRARY_DIR)/TAP/Harness.pbc \
    $(LIBRARY_DIR)/TAP/Parser.pbc \
    $(LIBRARY_DIR)/Test/Builder/Output.pbc \
    $(LIBRARY_DIR)/Test/Builder/Test.pbc \
    $(LIBRARY_DIR)/Test/Builder/Tester.pbc \
    $(LIBRARY_DIR)/Test/Builder/TestPlan.pbc \
    $(LIBRARY_DIR)/Test/Builder.pbc \
    $(LIBRARY_DIR)/Test/Class.pbc \
    $(LIBRARY_DIR)/Test/More.pbc \
    $(LIBRARY_DIR)/Tcl/Glob.pbc \
    $(LIBRARY_DIR)/TclLibrary.pbc \
    $(LIBRARY_DIR)/URI.pbc \
    $(LIBRARY_DIR)/URI/Escape.pbc \
    $(LIBRARY_DIR)/uuid.pbc \
    $(LIBRARY_DIR)/YAML/Dumper/Base.pbc \
    $(LIBRARY_DIR)/YAML/Dumper/Default.pbc \
    $(LIBRARY_DIR)/YAML/Dumper.pbc \
    $(LIBRARY_DIR)/STM.pbc \
    $(LIBRARY_DIR)/libpcre.pbc \
    $(LIBRARY_DIR)/postgres.pbc

FLUID_FILES_1 = \
    $(GEN_HEADERS) \
    $(GEN_SOURCES) \
    $(GEN_MODULES) \

FLUID_FILES_2 = \
    $(GEN_LIBRARY) \
    $(LIBRARY_DIR)/ProfTest/PIRProfile.pbc \
    $(LIBRARY_DIR)/ProfTest/NQPProfile.pbc \
    $(LIBRARY_DIR)/ProfTest/Matcher.pbc \
    $(LIBRARY_DIR)/ProfTest/Want.pbc \
    runtime/parrot/include/parrotlib.pbc


###############################################################################
#
# OTHER FILE GROUPS:
#
###############################################################################

# parrot.h and all the includes it causes to be included
PARROT_H_HEADERS = \
	$(INC_DIR)/parrot.h \
	$(INC_DIR)/config.h \
	$(INC_DIR)/settings.h \
	$(INC_DIR)/enums.h \
	$(INC_DIR)/platform.h \
	$(INC_DIR)/platform_interface.h \
	$(INC_DIR)/global_setup.h \
	$(INC_DIR)/caches.h \
	$(INC_DIR)/interpreter.h \
	$(INC_DIR)/datatypes.h \
	$(INC_DIR)/encoding.h \
	$(INC_DIR)/charset.h \
	$(INC_DIR)/string.h \
	$(INC_DIR)/string_primitives.h \
	$(INC_DIR)/hash.h \
	$(INC_DIR)/pmc_freeze.h \
	$(INC_DIR)/vtable.h \
	$(INC_DIR)/context.h \
	$(INC_DIR)/exceptions.h \
	$(INC_DIR)/warnings.h \
	$(INC_DIR)/memory.h \
	$(INC_DIR)/packfile.h \
	$(INC_DIR)/io.h \
	$(INC_DIR)/op.h \
	$(INC_DIR)/pmc.h \
	$(INC_DIR)/gc_api.h \
	$(INC_DIR)/string_funcs.h \
	$(INC_DIR)/misc.h \
	$(INC_DIR)/sub.h \
	$(INC_DIR)/call.h \
	$(INC_DIR)/key.h \
	$(INC_DIR)/exit.h \
	$(INC_DIR)/nci.h \
	$(INC_DIR)/thread.h \
	$(INC_DIR)/scheduler.h \
	$(INC_DIR)/longopt.h \
	$(INC_DIR)/oo.h \
	$(INC_DIR)/vtables.h \
	$(INC_DIR)/multidispatch.h \
	$(INC_DIR)/library.h \
	$(INC_DIR)/namespace.h \
	$(INC_DIR)/stat.h \
	$(INC_DIR)/hll.h \
	$(INC_DIR)/pbcversion.h \
	$(INC_DIR)/pobj.h \
	$(INC_DIR)/platform_limits.h \
	$(INC_DIR)/has_header.h \
	$(INC_DIR)/oplib.h \
	$(INC_DIR)/feature.h \
	$(INC_DIR)/debugger.h \
	$(INC_DIR)/core_types.h \
	$(INC_DIR)/core_pmcs.h \
	$(INC_DIR)/compiler.h \
	$(INC_DIR)/cclass.h \
	include/pmc/pmc_callcontext.h

# generated list of header files
GENERAL_H_FILES   = $(NONGEN_HEADERS) $(GEN_HEADERS) \


CHARSET_O_FILES   = @TEMP_charset_o@
CLASS_PMC_FILES   = @TEMP_pmc_classes_pmc@
CLASS_O_FILES     = @TEMP_pmc_classes_o@
CLASS_STR_FILES   = @TEMP_pmc_classes_str@
ENCODING_O_FILES  = @TEMP_encoding_o@

IO_O_FILES = \
    src/io/core$(O) \
    src/io/api$(O) \
    src/io/utf8$(O) \
    src/io/buffer$(O) \
    src/io/unix$(O) \
    src/io/win32$(O) \
    src/io/portable$(O) \
    src/io/filehandle$(O) \
    src/io/socket_api$(O) \
    src/io/socket_unix$(O) \
    src/io/socket_win32$(O)

INTERP_O_FILES = \
    src/string/api$(O) \
    src/ops/core_ops$(O) \
#IF(i386_has_gcc_cmpxchg):    src/atomic/gcc_x86$(O) \
    src/byteorder$(O) \
    src/string/charset$(O) \
    src/core_pmcs$(O) \
    src/datatypes$(O) \
    src/debug$(O) \
    src/dynext$(O) \
    src/embed$(O) \
    src/string/encoding$(O) \
    src/exceptions$(O) \
    src/exit$(O) \
    src/extend$(O) \
    src/extend_vtable$(O) \
    src/gc/alloc_memory$(O) \
    src/gc/api$(O) \
    src/gc/gc_ms$(O) \
    src/gc/gc_inf$(O) \
    src/gc/mark_sweep$(O) \
    src/gc/system$(O) \
    src/global_setup$(O) \
    src/hash$(O) \
    src/hll$(O) \
    src/call/pcc$(O)  \
    src/call/args$(O)  \
    src/interp/inter_cb$(O)  \
    src/interp/inter_create$(O)  \
    src/interp/inter_misc$(O)  \
    src/call/ops$(O)  \
    src/call/context$(O) \
    src/call/context_accessors$(O) \
    src/key$(O) \
    src/library$(O) \
    src/longopt$(O) \
    src/misc$(O) \
    src/multidispatch$(O) \
    src/namespace$(O) \
    src/nci/api$(O) \
    src/nci/core_thunks$(O) \
#IF(has_extra_nci_thunks): src/nci/extra_thunks$(O) \
    src/oo$(O) \
    src/packfile$(O) \
    src/packout$(O) \
    src/platform$(O) \
    src/pmc_freeze$(O) \
    src/pmc$(O) \
    src/runcore/main$(O)  \
    src/runcore/cores$(O) \
    src/runcore/profiling$(O) \
    src/scheduler$(O) \
    src/spf_render$(O) \
    src/spf_vtable$(O) \
    src/string/primitives$(O) \
    src/sub$(O) \
    src/thread$(O) \
    src/runcore/trace$(O) \
    src/utils$(O) \
    src/vtables$(O) \
    src/warnings$(O) \
    src/packfile/pf_items$(O) \
    @TEMP_atomic_o@ \
    @TEMP_gc_o@ \
#IF(platform_asm):    src/platform_asm$(O) \


OPS_FILES = @ops@

###############################################################################
#
# BUILD TARGET CONFIGURATIONS:
#
###############################################################################

# Executables
PARROT              = .@slash@@test_prog@$(EXE)
MINIPARROT          = .@slash@miniparrot$(EXE)
DIS                 = .@slash@pbc_disassemble$(EXE)
PDUMP               = .@slash@pbc_dump$(EXE)
PBC_MERGE           = .@slash@pbc_merge$(EXE)
PDB                 = .@slash@parrot_debugger$(EXE)
PBC_TO_EXE          = .@slash@pbc_to_exe$(EXE)
PARROT_CONFIG       = .@slash@parrot_config$(EXE)
PIRC                = .@slash@pirc$(EXE)
NQP_RX              = .@slash@parrot-nqp$(EXE)
NCI_THUNK_GEN       = .@slash@parrot_nci_thunk_gen$(EXE)
PROVE               = .@slash@parrot-prove$(EXE)
OPS2C               = .@slash@ops2c$(EXE)

# Installable executables
INSTALLABLEPARROT    = .@slash@installable_parrot$(EXE)
INSTALLABLEDIS       = .@slash@installable_pbc_disassemble$(EXE)
INSTALLABLEPDUMP     = .@slash@installable_pbc_dump$(EXE)
INSTALLABLEPBC_MERGE = .@slash@installable_pbc_merge$(EXE)
INSTALLABLEPBCTOEXE  = .@slash@installable_pbc_to_exe$(EXE)
INSTALLABLEPDB       = .@slash@installable_parrot_debugger$(EXE)
INSTALLABLECONFIG    = .@slash@installable_parrot_config$(EXE)
INSTALLABLENQP       = .@slash@installable_parrot-nqp$(EXE)
INSTALLABLENCITHUNKGEN = .@slash@installable_parrot_nci_thunk_gen$(EXE)
INSTALLABLEPROVE     = .@slash@installable_parrot-prove$(EXE)
INSTALLABLEOPS2C    = .@slash@installable_ops2c$(EXE)

# Libraries
LIBPARROT_STATIC    = @blib_dir@/@libparrot_static@
#IF(darwin):export DYLD_LIBRARY_PATH := @blib_dir@:$(DYLD_LIBRARY_PATH)
#IF(win32):LIBPARROT_SHARED  = @libparrot_shared@
#ELSE:LIBPARROT_SHARED  = @blib_dir@/@libparrot_shared@

# This line controls whether a static or shared library is built
# by Parrot's make.  It is not useful otherwise (e.g., in
# lib/Parrot/Config/Generated.pm or config_lib.pir).
LIBPARROT           = @libparrot_for_makefile_only@

#IF(has_icu):ICU_SHARED  = @icu_shared@
ALL_PARROT_LIBS     = @libparrot_linkflags@ $(ICU_SHARED) $(C_LIBS)

# dynamic extensions
DYNEXT_DIR          = runtime/parrot/dynext
LIBNCI_TEST_SO      = $(DYNEXT_DIR)/libnci_test$(LOAD_EXT)
LIBGLUTCB_SO        = $(DYNEXT_DIR)/libglutcb$(LOAD_EXT)
EXTRANCITHUNKS_SO   = $(DYNEXT_DIR)/extra_nci_thunks$(LOAD_EXT)

###############################################################################
#
# MAKE CONFIGURATION:
#
###############################################################################

# This is set to MAKE=$make if your $make command doesn't
# do it for you.
@make_set_make@
MAKE = @make_c@

# These need to be above lines that define suffix rules to be portable
# (certainly FreeBSD make doesn't grok the pir.pbc rule otherwise)

.SUFFIXES : .c .S .s .pmc .dump $(O) .str .pir .pbc

.c$(O) : # suffix rule (limited support)
	$(CC) $(CFLAGS) @optimize@ $(CC_WARN) -I$(@D) @cc_o_out@$@ -c $<

#UNLESS(win32):.s$(O) : # suffix rule (limited support)
#UNLESS(win32):	$(CC) $(CFLAGS) @optimize@ $(CC_WARN) -I$(@D) @cc_o_out@$@ -c $<

.pir.pbc : # suffix rule (limited support)
	$(PARROT) -o $@ $<

# Note: Several rules in this makefile are tagged with a "SUFFIX OVERRIDE"
# comment; this indicates that we have an explicit compilation rule for
# that particular C file; this is done so that we override various
# options for that file - to change optimization levels, or twiddle
# warnings. Each of those overrides should use the most specific settings
# possible for that file. When file-specific overrides are added during
# Configure, the override must be allowed for in this file.
# These will eventually be automatically generated.


###############################################################################
#
# USER TARGETS:
#
# These targets are supposed to be called by the user.
#
###############################################################################

all : \
    corevm \
    docs \
#IF(has_glut):    $(LIBGLUTCB_SO) \
    $(EXTRANCITHUNKS_SO) \
    $(DIS) \
    $(PARROT_CONFIG) \
    $(PBC_TO_EXE) \
    $(PBC_MERGE) \
    $(PDB) \
    $(PDUMP) \
    $(NQP_RX) \
    $(TGE_LIB_PBCS) \
    $(PGE_LIB_PBCS) \
    $(PCT_LIB_PBCS) \
    $(DATA_JSON_LIB_PBCS) \
    $(NQP_LIB_PBCS) \
    $(GEN_LIBRARY) \
    $(DYNOPLIBS_TARGETS) \
    $(LIBNCI_TEST_SO)

# We build DYNPMC_TARGET in corevm. It's kinda hack to test t/pmc/threads.t CLONE_LIBRARIES
corevm : \
    $(GEN_PM_INCLUDES) \
    PARROT_LIBS \
    $(PARROT) \
    runtime/parrot/include/parrotlib.pbc \
    runtime/parrot/include/config.fpmc \
    $(DYNPMC_TARGETS) \
    $(LIBRARY_DIR)/Test/More.pbc

$(GEN_LIBRARY) : $(PARROT) $(GEN_PASM_INCLUDES)

$(LIBRARY_DIR)/Digest/MD5.pbc: $(DYNEXT_DIR)/bit_ops$(LOAD_EXT)

$(LIBRARY_DIR)/Archive/Zip.pbc: $(DYNEXT_DIR)/sys_ops$(LOAD_EXT) $(DYNEXT_DIR)/io_ops$(LOAD_EXT)

$(LIBRARY_DIR)/Configure/genfile.pbc: $(DYNEXT_DIR)/sys_ops$(LOAD_EXT)

# Message.pbc and distutils.pbc load io_ops to work around TT #1663
638	$(LIBRARY_DIR)/HTTP/Message.pbc: $(DYNEXT_DIR)/sys_ops$(LOAD_EXT) $(DYNEXT_DIR)/io_ops$(LOAD_EXT)

$(LIBRARY_DIR)/distutils.pbc: $(DYNEXT_DIR)/sys_ops$(LOAD_EXT) $(DYNEXT_DIR)/io_ops$(LOAD_EXT)

$(LIBRARY_DIR)/pcre.pbc: $(DYNEXT_DIR)/sys_ops$(LOAD_EXT)

$(LIBRARY_DIR)/LWP/Protocol.pbc: $(DYNEXT_DIR)/io_ops$(LOAD_EXT) $(DYNEXT_DIR)/sys_ops$(LOAD_EXT)

$(LIBRARY_DIR)/Test/More.pbc:

$(LIBRARY_DIR)/Archive/Tar.pbc: $(DYNEXT_DIR)/io_ops$(LOAD_EXT)

$(LIBRARY_DIR)/osutils.pbc: $(DYNEXT_DIR)/io_ops$(LOAD_EXT)

$(LIBRARY_DIR)/Config/JSON.pbc: $(DYNEXT_DIR)/io_ops$(LOAD_EXT) $(DYNEXT_DIR)/sys_ops$(LOAD_EXT)

$(LIBRARY_DIR)/LWP/UserAgent.pbc: $(DYNEXT_DIR)/io_ops$(LOAD_EXT)

# constant string support
.c.str : # suffix rule (limited support)
	$(PERL) $(BUILD_TOOLS_DIR)/c2str.pl $< > $@

STR_FILES = \
    src/debug.str \
    src/dynext.str \
    src/exceptions.str \
    src/global_setup.str \
    src/hll.str \
    src/call/pcc.str \
    src/call/args.str \
    src/interp/inter_cb.str \
    src/interp/inter_create.str \
    src/interp/inter_misc.str \
    src/io/api.str \
    src/key.str \
    src/library.str \
    src/multidispatch.str \
    src/namespace.str \
    src/nci/api.str \
    src/nci/core_thunks.str \
#IF(has_extra_nci_thunks): src/nci/extra_thunks.str \
    src/packfile.str \
    src/pmc.str \
    src/pmc_freeze.str \
    src/oo.str \
    src/runcore/cores.str \
    src/runcore/main.str \
    src/runcore/profiling.str \
    src/scheduler.str \
    src/spf_render.str \
    src/spf_vtable.str \
    src/string/api.str \
    src/sub.str \
    src/embed.str \
    \
    $(CLASS_STR_FILES)

src/string/private_cstring.h : $(STR_FILES) $(BUILD_TOOLS_DIR)/c2str.pl
	$(PERL) $(BUILD_TOOLS_DIR)/c2str.pl --all

H2INC = $(BUILD_TOOLS_DIR)/h2inc.pl

# classes PMC build utils and rules
PMC2C  = $(PERL) $(BUILD_TOOLS_DIR)/pmc2c.pl @no_lines_flag@
PMC2CD = $(PERL) $(BUILD_TOOLS_DIR)/pmc2c.pl --dump @no_lines_flag@
PMC2CC = $(PERL) $(BUILD_TOOLS_DIR)/pmc2c.pl --c @no_lines_flag@
PMC2CV = $(PERL) $(BUILD_TOOLS_DIR)/pmc2c.pl --vtable @no_lines_flag@

.pmc.dump : # suffix rule (limited support)
	$(PMC2CD) $<

.pmc.c : # suffix rule (limited support)
	$(PMC2CC) $<

vtable.dump : src/vtable.tbl lib/Parrot/Pmc2c/PCCMETHOD_BITS.pm
	$(PMC2CV)

# This is a listing of all targets meant to be called by users
help :
	@echo ""
	@echo "Following targets are available for the user:"
	@echo ""
	@echo "Executables:"
	@echo "  all:               'parrot' and the documentation."
	@echo "                     This is the default."
	@echo ""
	@echo "  world:             'all' and 'parrot_utils'."
	@echo "  installable:       same as 'world', but targets for installation"
	@echo ""
	@echo "  parrot_utils:      $(PDUMP), $(DIS), $(PDB), $(PBC_MERGE) and $(PBC_TO_EXE) $(PARROT_CONFIG)"
	@echo " $(PDUMP):"
	@echo "                     Parrot Dumper"
	@echo " $(DIS):"
	@echo "                     Parrot Disassembler"
	@echo " $(PDB):"
	@echo "                     Parrot Debugger"
	@echo " $(PBC_MERGE):"
	@echo "                     Merge bytecode files"
	@echo " $(PBC_TO_EXE):"
	@echo "                     Generate C, compile, and link bytecode files"
	@echo " $(PARROT_CONFIG):"
	@echo "                     Provide Parrot configuration information"
	@echo ""
	@echo "Installation:"
	@echo "  install:           Install under '$(PREFIX)' on Unix systems."
	@echo "  install-dev:       Same as 'install'."
	@echo "  install-bin:       Install only files needed for Parrot runtime."
	@echo "  install-dev-only:  Install only files needed for Parrot development."
	@echo "  install-doc:       Install documentation files & examples."
	@echo ""
	@echo "Documentation:"
	@echo "  help:              Print this help message."
	@echo "  docs:              Generate documentation from POD in the sources."
	@echo "  html:              Generate HTML documentation from POD in the sources."
	@echo "  html-clean:        Remove the HTML documentation."
	@echo "  htmlhelp:          Compile HTML documentation (CHM format)."
	@echo ""
	@echo "Testing:"
	@echo "  test:              Run the standard test suite."
	@echo "  coretest:          Run the minimal 'core functionality' suite."
	@echo "  codetest:          Run file metadata and coding standards tests."
	@echo "  fulltest:          Run the full test suite under many runcores."
	@echo "  test<runcore>:     Run the test suite with a specified runcore."
	@echo "                     Valid runcores are b, C, f, g, j, r, S."
	@echo "  src_tests:         Run test in C-file."
	@echo "  run_tests:         Command line and various environments."
	@echo "  perl_tests:        Test the Perl modules in the distribution."
	@echo "  codingstd_tests:   Test pdd07_codingstd."
	@echo "  testexec:          Testing the exec runcore."
	@echo "  benchmark_tests:   Run all benchmarks."
	@echo "  warnings_tests:    Run standard test suite with warnings enabled."
	@echo "  manitest:          Check for new and missing files."
	@echo "  buildtools_tests:  Test build tool pmc2c.pl."
	@echo "  manifest_tests:    Test code underlying mk_manifest_and_skip.pl."
	@echo "  examples_tests:    Test the example scripts."
	@echo ""
	@echo "Smoke Testing:"
	@echo "  smolder_test:      Run the test suite and send report to the smolder server"
	@echo "  smolder_coretest:  Run the minimal 'core functionality' suite and send report to the smolder server."
	@echo "  smoke:             Alias for smolder_test"
	@echo ""
	@echo "Benchmarks:"
	@echo "  mopsbench:         Million operations"
	@echo ""
	@echo "Cleaning:"
	@echo "  clean:             Basic cleaning up."
	@echo "  archclean:         Remove any platform dependent files."
	@echo "  realclean:         Removes also files generated by 'Configure.pl'"
	@echo "  distclean:         Removes also anything built, in theory."
	@echo "  svnclobber:        *Dangerous*: remove everything not in svn."
	@echo "  reconfig:          'clean' and redo configuration."
	@echo ""
	@echo "Fetch from source repository:"
	@echo "  update:            svn update."
	@echo "  status:            svn status."
	@echo "  patch:             Create a patch to attach to https://trac.parrot.org/"
	@echo ""
	@echo "Development:"
	@echo "  lint:              An alias for sunlint."
	@echo "  bsdlint:           Code checking with bsdlint."
	@echo "  sunlint:           Code checking with Sun Studio's sunlint."
	@echo "  splint:            Code checking with splint."
	@echo "  splint-all:        Splint all of Parrot, for the masochist only."
	@echo "  headerizer:        Recreate header files for C-source files"
	@echo "  apilist:           Show list of PARROT_API functions"
	@echo "  exportlist:        Show list of PARROT_EXPORT functions"
	@echo "  malloclist:        Show list of PARROT_MALLOC functions"
	@echo "  cover:             Run test suite coverage analysis."
	@echo "  tags-vi:           Create tags for the vi editor."
	@echo "  tags-emacs:        Create tags for the Emacs editor."
	@echo "  perlcritic:        Check Perl code with Perl::Critic."
	@echo "  bootstrap-ops:     Generate C code from .ops files."
	@echo ""
	@echo "Release:"
	@echo "  release:           Create a tarball."
	@echo "  win32-inno-installer:  Create MSWin32 setup."
	@echo ""
	@echo "Examples:"
	@echo "  hello:             'Hello World' as an executable."
	@echo ""

world : all parrot_utils

parrot_utils : $(PDUMP) $(DIS) $(PDB) $(PBC_MERGE) $(PBC_TO_EXE) $(PARROT_CONFIG) src/install_config$(O) $(PROVE) $(OPS2C)

installable: all $(INSTALLABLEPARROT) $(INSTALLABLEPDUMP) $(INSTALLABLEDIS) $(INSTALLABLEPDB) $(INSTALLABLEPBC_MERGE) $(INSTALLABLEPBCTOEXE) $(INSTALLABLECONFIG) $(INSTALLABLENQP) $(INSTALLABLENCITHUNKGEN) $(INSTALLABLEPROVE) $(INSTALLABLEOPS2C)

bootstrap-ops : $(OPS2C)
	$(OPS2C) --core --quiet
	$(MAKE) .

runtime/parrot/include/parrotlib.pbc: runtime/parrot/library/parrotlib.pir $(PARROT) $(GEN_PASM_INCLUDES)
	$(PARROT) -o $@ runtime/parrot/library/parrotlib.pir

runtime/parrot/include/config.fpmc : myconfig config_lib.pir \
    runtime/parrot/include/datatypes.pasm $(MINIPARROT)
	$(MINIPARROT) -Iruntime/parrot/include config_lib.pir > $@

$(PARROT) : src/main$(O) $(GEN_HEADERS) $(LIBPARROT) \
    src/parrot_config$(O) \
    $(MINIPARROT)
	$(LINK) @ld_out@$@ \
	src/main$(O) src/parrot_config$(O) \
	@rpath_blib@ $(ALL_PARROT_LIBS) $(LINKFLAGS) $(LINK_DYNAMIC)
#IF(win32):	if exist $@.manifest mt.exe -nologo -manifest $@.manifest -outputresource:$@;1

$(PBC_TO_EXE) : tools/dev/pbc_to_exe.pir runtime/parrot/library/config.pir $(PARROT) $(DYNEXT_DIR)/os$(LOAD_EXT) $(DYNEXT_DIR)/file$(LOAD_EXT)
	$(PARROT) -o pbc_to_exe.pbc tools/dev/pbc_to_exe.pir
	$(PARROT) pbc_to_exe.pbc pbc_to_exe.pbc

parrot_nci_thunk_gen.pbc : tools/dev/nci_thunk_gen.pir $(DATA_JSON_LIB_PBCS) $(PARROT)
	$(PARROT) -o parrot_nci_thunk_gen.pbc tools/dev/nci_thunk_gen.pir

$(NCI_THUNK_GEN) : parrot_nci_thunk_gen.pbc $(PBC_TO_EXE)
	$(PBC_TO_EXE) parrot_nci_thunk_gen.pbc

parrot-prove.pbc : runtime/parrot/bin/prove.pir $(PARROT)
	$(PARROT) -o parrot-prove.pbc runtime/parrot/bin/prove.pir

$(PROVE) : parrot-prove.pbc $(PARROT) $(PBC_TO_EXE)
	$(PBC_TO_EXE) parrot-prove.pbc

$(PARROT_CONFIG) : tools/util/parrot-config.pir $(PARROT) $(PBC_TO_EXE)
	$(PARROT) -o parrot_config.pbc tools/util/parrot-config.pir
	$(PARROT) pbc_to_exe.pbc parrot_config.pbc

$(MINIPARROT) : src/main$(O) $(GEN_HEADERS) $(LIBPARROT) \
    src/null_config$(O)
	$(LINK) @ld_out@$@ src/main$(O) src/null_config$(O) \
	@rpath_blib@ $(ALL_PARROT_LIBS) $(LINKFLAGS)
#IF(win32):	if exist $@.manifest mt.exe -nologo -manifest $@.manifest -outputresource:$@;1

$(INSTALLABLEPARROT) : src/main$(O) $(GEN_HEADERS) $(LIBPARROT) \
    src/install_config$(O) \
    $(PARROT)
	$(LINK) @ld_out@$@ \
    src/main$(O) src/install_config$(O) \
    @rpath_lib@ $(ALL_PARROT_LIBS) $(LINKFLAGS)
#IF(win32):	if exist $@.manifest mt.exe -nologo -manifest $@.manifest -outputresource:$@;1

$(INC_DIR)/context.h : include/pmc/pmc_callcontext.h

$(INC_DIR)/pbcversion.h : PBC_COMPAT
	$(PERL) $(BUILD_TOOLS_DIR)/pbcversion_h.pl > $(INC_DIR)/pbcversion.h

src/parrot_config.c :  runtime/parrot/include/config.fpmc \
    $(BUILD_TOOLS_DIR)/parrot_config_c.pl
	$(PERL) $(BUILD_TOOLS_DIR)/parrot_config_c.pl > \
    src/parrot_config.c

src/install_config.c :  install_config.fpmc \
    $(BUILD_TOOLS_DIR)/parrot_config_c.pl
	$(PERL) $(BUILD_TOOLS_DIR)/parrot_config_c.pl --install > \
    src/install_config.c

src/null_config.c : myconfig $(BUILD_TOOLS_DIR)/parrot_config_c.pl
	$(PERL) $(BUILD_TOOLS_DIR)/parrot_config_c.pl --mini > \
    src/null_config.c

install_config.fpmc : myconfig config_lib.pir $(PARROT)
	@echo "Invoking Parrot to generate install_config.fpmc"
	$(PARROT) config_lib.pir --install > $@

src/parrot_config$(O) : $(PARROT_H_HEADERS) src/parrot_config.c

src/install_config$(O) : $(PARROT_H_HEADERS) src/install_config.c

src/null_config$(O) : $(PARROT_H_HEADERS) src/null_config.c

src/oo$(O) : $(PARROT_H_HEADERS) include/pmc/pmc_class.h src/oo.c \
    include/pmc/pmc_object.h src/oo.str $(INC_DIR)/oo_private.h

src/scheduler$(O) : $(PARROT_H_HEADERS) src/scheduler.str src/scheduler.c \
	include/pmc/pmc_scheduler.h include/pmc/pmc_task.h \
	include/pmc/pmc_timer.h \
	$(INC_DIR)/scheduler_private.h \
	$(INC_DIR)/runcore_api.h

src/io/core$(O) : $(PARROT_H_HEADERS) src/io/io_private.h src/io/core.c

src/io/socket_api$(O) : $(PARROT_H_HEADERS) src/io/io_private.h \
    src/io/api.str include/pmc/pmc_socket.h src/io/socket_api.c

src/io/socket_unix$(O) : $(PARROT_H_HEADERS) include/pmc/pmc_socket.h \
    src/io/io_private.h src/io/socket_unix.c

src/io/socket_win32$(O) : $(PARROT_H_HEADERS) \
	src/io/io_private.h \
	include/pmc/pmc_socket.h \
	src/io/socket_win32.c

O_FILES = \
    $(INTERP_O_FILES) \
    $(CHARSET_O_FILES) \
    $(IO_O_FILES) \
    $(CLASS_O_FILES) \
    $(ENCODING_O_FILES) \
    $(IMCC_O_FILES)

lib_deps_object : $(O_FILES)
	$(PERL) tools/dev/lib_deps.pl object $(O_FILES)

lib_deps_source : $(GENERAL_H_FILES)
	$(PERL) tools/dev/lib_deps.pl source all_source

lib_deps : lib_deps_object lib_deps_source

# XXX changes don't always propagate into libparrot
# e.g. when I change debug:fataly to xfataly, nm still shows the old symbol
# and parrot builds fine (except for the unproto warning
# so always delete the lib -leo

PARROT_LIBS: \
#IF(has_static_linking):  $(LIBPARROT_STATIC) \
#IF(has_dynamic_linking): $(LIBPARROT_SHARED)

$(LIBPARROT_STATIC) : $(O_FILES)
	$(MKPATH) @blib_dir@
	$(AR_CR) @ar_out@$@ @ar_extra@ $(O_FILES)
#IF(win32):	if exist $@.manifest mt.exe -nologo -manifest $@.manifest -outputresource:$@;2
	$(RANLIB) $@

$(LIBPARROT_SHARED) : $(O_FILES)
	$(MKPATH) @blib_dir@
	$(LD) $(LD_SHARE_FLAGS) $(LDFLAGS) @ld_out@$@ @libparrot_soname@ \
#IF(cygwin):		-Wl,--out-implib=libparrot.dll.a \
#IF(win32 and cc==gcc):		-Wl,--out-implib=libparrot.lib \
		$(O_FILES) $(C_LIBS) $(ICU_SHARED)
#IF(win32):	if exist $@.manifest mt.exe -nologo -manifest $@.manifest -outputresource:$@;2
#IF(libparrot_shared_alias):	( cd @blib_dir@ ; ln -sf @libparrot_shared@ @libparrot_shared_alias@ )


$(INSTALLABLECONFIG) : src/install_config$(O) $(PARROT_CONFIG) $(PBC_TO_EXE)
	$(PARROT) -o parrot_config.pbc tools/util/parrot-config.pir
	$(PBC_TO_EXE) parrot_config.pbc --install

$(INSTALLABLEPBCTOEXE) : $(PBC_TO_EXE) src/install_config$(O)
	$(PBC_TO_EXE) pbc_to_exe.pbc --install

$(INSTALLABLENCITHUNKGEN) : parrot_nci_thunk_gen.pbc $(PBC_TO_EXE) src/install_config$(O)
	$(PBC_TO_EXE) parrot_nci_thunk_gen.pbc --install

$(INSTALLABLEPROVE) : parrot-prove.pbc $(PBC_TO_EXE) src/install_config$(O)
	$(PBC_TO_EXE) parrot-prove.pbc --install

#
# Parrot Debugger
#

src/parrot_debugger$(O) : $(PARROT_H_HEADERS) src/parrot_debugger.c \
	$(INC_DIR)/embed.h \
	$(INC_DIR)/runcore_api.h

$(PDB) : src/parrot_debugger$(O) src/parrot_config$(O) $(LIBPARROT)
	$(LINK) @ld_out@$@ \
    src/parrot_debugger$(O) \
    src/parrot_config$(O) \
    @rpath_blib@ $(ALL_PARROT_LIBS) $(LINKFLAGS)
#IF(win32):	if exist $@.manifest mt.exe -nologo -manifest $@.manifest -outputresource:$@;1

$(INSTALLABLEPDB) : src/parrot_debugger$(O) $(LIBPARROT) src/parrot_config$(O)
	$(LINK) @ld_out@$@ \
    src/parrot_debugger$(O) \
    src/parrot_config$(O) \
    @rpath_lib@ $(ALL_PARROT_LIBS) $(LINKFLAGS)
#IF(win32):	if exist $@.manifest mt.exe -nologo -manifest $@.manifest -outputresource:$@;1

#
# Parrot Disassembler
#

src/pbc_disassemble$(O) : $(INC_DIR)/embed.h $(PARROT_H_HEADERS) \
    src/pbc_disassemble.c

$(DIS) : src/pbc_disassemble$(O) $(LIBPARROT)
	$(LINK) @ld_out@$@ \
    src/pbc_disassemble$(O) \
    @rpath_blib@ $(ALL_PARROT_LIBS) $(LINKFLAGS)
#IF(win32):	if exist $@.manifest mt.exe -nologo -manifest $@.manifest -outputresource:$@;1

$(INSTALLABLEDIS) : src/pbc_disassemble$(O) \
	src/install_config$(O) $(LIBPARROT)
	$(LINK) @ld_out@$@ \
    src/pbc_disassemble$(O) \
    @rpath_lib@ $(ALL_PARROT_LIBS) $(LINKFLAGS)
#IF(win32):	if exist $@.manifest mt.exe -nologo -manifest $@.manifest -outputresource:$@;1

#
# Parrot Dump
#
src/packdump$(O) : $(PARROT_H_HEADERS) include/pmc/pmc_sub.h \
    include/pmc/pmc_key.h src/packdump.c

$(PDUMP) : src/pbc_dump$(O) src/packdump$(O) $(LIBPARROT)
	$(LINK) @ld_out@$@ \
    src/pbc_dump$(O) \
    src/packdump$(O) @rpath_blib@ $(ALL_PARROT_LIBS) $(LINKFLAGS)
#IF(win32):	if exist $@.manifest mt.exe -nologo -manifest $@.manifest -outputresource:$@;1

src/pbc_dump$(O) : $(INC_DIR)/embed.h  $(INC_DIR)/oplib/ops.h \
	$(PARROT_H_HEADERS) src/pbc_dump.c

$(INSTALLABLEPDUMP) : src/pbc_dump$(O) src/packdump$(O) \
	src/install_config$(O) $(LIBPARROT)
	$(LINK) @ld_out@$@ \
    src/pbc_dump$(O) \
    src/packdump$(O) \
    @rpath_lib@ $(ALL_PARROT_LIBS) $(LINKFLAGS)
#IF(win32):	if exist $@.manifest mt.exe -nologo -manifest $@.manifest -outputresource:$@;1



#
# Parrot Bytecode File Merger
#

$(PBC_MERGE) : src/pbc_merge$(O) $(LIBPARROT) src/parrot_config$(O)
	$(LINK) @ld_out@$@ \
    src/pbc_merge$(O) \
    src/parrot_config$(O) \
    @rpath_blib@ $(ALL_PARROT_LIBS) $(LINK_DYNAMIC) $(LINKFLAGS)
#IF(win32):	if exist $@.manifest mt.exe -nologo -manifest $@.manifest -outputresource:$@;1

$(INSTALLABLEPBC_MERGE) : src/pbc_merge$(O) $(LIBPARROT) $(INSTALLABLECONFIG)
	$(LINK) @ld_out@$@ \
    src/pbc_merge$(O) \
    src/install_config$(O) \
    @rpath_lib@ $(ALL_PARROT_LIBS) $(LINKFLAGS)
#IF(win32):	if exist $@.manifest mt.exe -nologo -manifest $@.manifest -outputresource:$@;1

#
# Profiling runcore test supporting code
#

$(LIBRARY_DIR)/ProfTest.pbc: $(LIBRARY_DIR)/ProfTest/PIRProfile.pbc \
	$(LIBRARY_DIR)/ProfTest/NQPProfile.pbc $(LIBRARY_DIR)/ProfTest/Matcher.pbc \
	$(LIBRARY_DIR)/ProfTest/Want.pbc
	$(PBC_MERGE) -o $@ $(LIBRARY_DIR)/ProfTest/PIRProfile.pbc \
	$(LIBRARY_DIR)/ProfTest/NQPProfile.pbc $(LIBRARY_DIR)/ProfTest/Matcher.pbc \
	$(LIBRARY_DIR)/ProfTest/Want.pbc


$(LIBRARY_DIR)/ProfTest/PIRProfile.pbc: $(LIBRARY_DIR)/ProfTest/PIRProfile.pir
	$(PARROT) -o $@ $(LIBRARY_DIR)/ProfTest/PIRProfile.pir

$(LIBRARY_DIR)/ProfTest/PIRProfile.pir: $(LIBRARY_DIR)/ProfTest/PIRProfile.nqp $(NQP_RX)
	$(NQP_RX) --target=pir $(LIBRARY_DIR)/ProfTest/PIRProfile.nqp > $@


$(LIBRARY_DIR)/ProfTest/NQPProfile.pbc: $(LIBRARY_DIR)/ProfTest/NQPProfile.pir
	$(PARROT) -o $@ $(LIBRARY_DIR)/ProfTest/NQPProfile.pir

$(LIBRARY_DIR)/ProfTest/NQPProfile.pir: $(LIBRARY_DIR)/ProfTest/NQPProfile.nqp $(NQP_RX)
	$(NQP_RX) --target=pir $(LIBRARY_DIR)/ProfTest/NQPProfile.nqp > $@


$(LIBRARY_DIR)/ProfTest/Want.pbc: $(LIBRARY_DIR)/ProfTest/Want.pir
	$(PARROT) -o $@ $(LIBRARY_DIR)/ProfTest/Want.pir

$(LIBRARY_DIR)/ProfTest/Want.pir: $(LIBRARY_DIR)/ProfTest/Want.nqp $(NQP_RX)
	$(NQP_RX) --target=pir $(LIBRARY_DIR)/ProfTest/Want.nqp > $@


$(LIBRARY_DIR)/ProfTest/Matcher.pbc: $(LIBRARY_DIR)/ProfTest/Matcher.pir
	$(PARROT) -o $@ $(LIBRARY_DIR)/ProfTest/Matcher.pir

$(LIBRARY_DIR)/ProfTest/Matcher.pir: $(LIBRARY_DIR)/ProfTest/Matcher.nqp $(NQP_RX)
	$(NQP_RX) --target=pir $(LIBRARY_DIR)/ProfTest/Matcher.nqp > $@



###############################################################################
#
# Other Dependencies and Build Rules:
#
###############################################################################


runtime/parrot/include/interpflags.pasm : $(INC_DIR)/interpreter.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/interpreter.h $@
runtime/parrot/include/interpdebug.pasm : $(INC_DIR)/interpreter.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/interpreter.h $@
runtime/parrot/include/interptrace.pasm : $(INC_DIR)/interpreter.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/interpreter.h $@
runtime/parrot/include/interpcores.pasm : $(INC_DIR)/interpreter.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/interpreter.h $@
runtime/parrot/include/cloneflags.pasm  : $(INC_DIR)/interpreter.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/interpreter.h $@
runtime/parrot/include/iglobals.pasm    : $(INC_DIR)/interpreter.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/interpreter.h $@
runtime/parrot/include/sysinfo.pasm     : $(INC_DIR)/interpreter.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/interpreter.h $@

runtime/parrot/include/interpinfo.pasm : $(INC_DIR)/gc_api.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/gc_api.h $@

runtime/parrot/include/timer.pasm : $(INC_DIR)/scheduler.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/scheduler.h $@

runtime/parrot/include/pmctypes.pasm : $(INC_DIR)/core_pmcs.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/core_pmcs.h $@

runtime/parrot/include/stdio.pasm  : $(INC_DIR)/io.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/io.h $@
runtime/parrot/include/socket.pasm : $(INC_DIR)/io.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/io.h $@

runtime/parrot/include/hash_key_type.pasm : $(INC_DIR)/hash.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/hash.h $@

runtime/parrot/include/iterator.pasm : $(INC_DIR)/enums.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/enums.h $@
runtime/parrot/include/call_bits.pasm : $(INC_DIR)/enums.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/enums.h $@
lib/Parrot/Pmc2c/PCCMETHOD_BITS.pm : $(INC_DIR)/enums.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/enums.h $@

runtime/parrot/include/libpaths.pasm : $(INC_DIR)/library.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/library.h $@

runtime/parrot/include/dlopenflags.pasm : $(INC_DIR)/platform_interface.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/platform_interface.h $@

runtime/parrot/include/datatypes.pasm : $(INC_DIR)/datatypes.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/datatypes.h $@

runtime/parrot/include/stat.pasm : $(INC_DIR)/stat.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/stat.h $@

runtime/parrot/include/stringinfo.pasm : $(INC_DIR)/string.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/string.h $@

runtime/parrot/include/longopt.pasm : $(INC_DIR)/longopt.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/longopt.h $@

runtime/parrot/include/cclass.pasm : $(INC_DIR)/cclass.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/cclass.h $@

runtime/parrot/include/packfile_segments.pasm : $(INC_DIR)/packfile.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/packfile.h $@
runtime/parrot/include/packfile_constants.pasm : $(INC_DIR)/packfile.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/packfile.h $@
runtime/parrot/include/packfile_annotation_key_type.pasm : $(INC_DIR)/packfile.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/packfile.h $@

runtime/parrot/include/except_types.pasm : $(INC_DIR)/exceptions.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/exceptions.h $@
runtime/parrot/include/except_severity.pasm : $(INC_DIR)/exceptions.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/exceptions.h $@

runtime/parrot/include/warnings.pasm : $(INC_DIR)/warnings.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/warnings.h $@
runtime/parrot/include/errors.pasm : $(INC_DIR)/warnings.h $(H2INC)
	$(PERL) $(H2INC) $(INC_DIR)/warnings.h $@

runtime/parrot/include/tm.pasm : src/utils.c $(H2INC)
	$(PERL) $(H2INC) src/utils.c $@


###############################################################################
#
# Examples (Assembly):
#
###############################################################################

examples-clean:
	$(RM_F) \
    examples/mops/mops$(O) \
    examples/mops/mops$(EXE) \
    examples/pasm/hello.pbc \
    examples/pasm/hello$(O) \
    examples/pasm/hello$(EXE) \
    generated_hello.pbc

# hello
hello: test_prep examples/pasm/hello$(EXE)
	.@slash@examples@slash@pasm@slash@hello$(EXE) "from your friendly makefile"

examples/pasm/hello.pbc: examples/pasm/hello.pasm
	$(PARROT) -o examples/pasm/hello.pbc examples/pasm/hello.pasm

# The -o option of parrot did not work with the object file extension ".o"
# so as work around pbc_to_exe is used and the original commands are only
# commented out so it can easily switched back.
#examples/pasm/hello$(O): examples/pasm/hello.pbc
#	$(PARROT) -o examples/pasm/hello$(O) examples/pasm/hello.pbc
#
#examples/pasm/hello$(EXE): examples/pasm/hello$(O)
#	$(MAKE) . EXEC=examples/pasm/hello exec
examples/pasm/hello$(EXE): examples/pasm/hello.pbc $(PBC_TO_EXE)
	$(PBC_TO_EXE) examples/pasm/hello.pbc



###############################################################################
#
# Dependencies:
#
###############################################################################

src/byteorder$(O) : $(PARROT_H_HEADERS) src/byteorder.c

src/datatypes$(O) : $(PARROT_H_HEADERS) src/datatypes.c

src/extend_vtable$(O) : $(PARROT_H_HEADERS) \
	$(INC_DIR)/extend.h $(INC_DIR)/extend_vtable.h src/extend_vtable.c

src/global_setup$(O) : $(PARROT_H_HEADERS) src/global_setup.str src/global_setup.c

src/namespace$(O) : $(PARROT_H_HEADERS) src/namespace.str src/namespace.c \
	include/pmc/pmc_sub.h

src/pmc$(O) : include/pmc/pmc_class.h src/pmc.c \
	src/pmc.str $(PARROT_H_HEADERS)

src/pmc_freeze$(O) : $(PARROT_H_HEADERS) src/pmc_freeze.str src/pmc_freeze.c

src/hash$(O) : $(PARROT_H_HEADERS) include/pmc/pmc_key.h src/hash.c

src/library$(O) : $(PARROT_H_HEADERS) src/library.str src/library.c\
	$(INC_DIR)/dynext.h

$(INC_DIR)/extend_vtable.h src/extend_vtable.c src/vtable.h : src/vtable.tbl $(BUILD_TOOLS_DIR)/vtable_extend.pl lib/Parrot/Vtable.pm
	$(PERL) $(BUILD_TOOLS_DIR)/vtable_extend.pl

src/key$(O) : $(PARROT_H_HEADERS) src/key.str src/key.c \
	include/pmc/pmc_key.h

src/gc/mark_sweep$(O) : $(PARROT_H_HEADERS) src/gc/gc_private.h src/gc/mark_sweep.c

src/gc/gc_ms$(O) : $(PARROT_H_HEADERS) src/gc/gc_private.h src/gc/gc_ms.c

src/gc/gc_inf$(O) : $(PARROT_H_HEADERS) src/gc/gc_private.h src/gc/gc_inf.c

src/gc/api$(O) : $(PARROT_H_HEADERS) src/gc/gc_private.h src/gc/api.c

src/gc/alloc_resources$(O) : $(PARROT_H_HEADERS) \
	src/gc/gc_private.h src/gc/alloc_resources.c

src/hll$(O) : $(PARROT_H_HEADERS) src/hll.str $(INC_DIR)/dynext.h src/hll.c

src/platform$(O) : $(PARROT_H_HEADERS) src/platform.c

#IF(platform_asm):src/platform_asm$(O) : $(PARROT_H_HEADERS)
#IF(platform_asm):
src/core_pmcs$(O) : $(PARROT_H_HEADERS) src/core_pmcs.c

src/runcore/trace$(O) : include/pmc/pmc_sub.h src/runcore/trace.c \
	$(INC_DIR)/oplib/ops.h $(INC_DIR)/runcore_trace.h \
	$(PARROT_H_HEADERS)

src/debug$(O) : $(INC_DIR)/embed.h $(INC_DIR)/extend.h \
	$(PARROT_H_HEADERS) src/debug.c \
	$(INC_DIR)/oplib/ops.h \
	$(INC_DIR)/runcore_api.h $(INC_DIR)/runcore_trace.h \
	src/debug.str include/pmc/pmc_key.h \
	include/pmc/pmc_continuation.h \
	$(INC_DIR)/extend_vtable.h

src/sub$(O) : $(PARROT_H_HEADERS) $(INC_DIR)/oplib/ops.h \
	src/sub.str src/sub.c \
	include/pmc/pmc_sub.h include/pmc/pmc_continuation.h

src/string/api$(O) : $(PARROT_H_HEADERS) src/string/api.str \
	src/string/private_cstring.h src/string/api.c

src/string/primitives$(O) : $(PARROT_H_HEADERS) src/string/primitives.c

src/longopt$(O) : $(PARROT_H_HEADERS) src/longopt.c

src/dynext$(O) : $(PARROT_H_HEADERS) $(INC_DIR)/dynext.h \
	src/dynext.str include/pmc/pmc_parrotlibrary.h src/dynext.c

src/exceptions$(O) : $(PARROT_H_HEADERS) \
	src/exceptions.str src/exceptions.c \
	include/pmc/pmc_continuation.h

src/thread$(O) : $(PARROT_H_HEADERS) $(INC_DIR)/atomic.h src/thread.c \
	include/pmc/pmc_sub.h \
	include/pmc/pmc_parrotinterpreter.h \
	$(INC_DIR)/runcore_api.h

## SUFFIX OVERRIDE - dynloaded files need cc_shared
src/extend$(O) : $(PARROT_H_HEADERS) $(INC_DIR)/extend.h \
    include/pmc/pmc_sub.h $(INC_DIR)/extend_vtable.h src/extend.c
	$(CC) $(CFLAGS) @optimize::src/extend.c@ @ccwarn::src/extend.c@ @cc_shared@ -I$(@D) @cc_o_out@$@ -c src/extend.c

src/runcore/main$(O) : \
	src/runcore/main.c \
	src/runcore/main.str \
	include/pmc/pmc_parrotlibrary.h \
	$(INC_DIR)/dynext.h $(INC_DIR)/oplib/core_ops.h \
	$(INC_DIR)/oplib/ops.h \
	$(PARROT_H_HEADERS) $(INC_DIR)/runcore_api.h \
	$(INC_DIR)/runcore_profiling.h

src/runcore/profiling$(O) : src/runcore/profiling.str src/runcore/profiling.c \
	include/pmc/pmc_sub.h \
	include/pmc/pmc_namespace.h \
	$(INC_DIR)/oplib/core_ops.h $(INC_DIR)/runcore_api.h \
	$(INC_DIR)/runcore_profiling.h $(INC_DIR)/embed.h \
	$(PARROT_H_HEADERS)

src/call/args$(O) : \
	$(PARROT_H_HEADERS) $(INC_DIR)/oplib/ops.h \
	src/call/args.c \
	src/call/args.str \
	include/pmc/pmc_key.h \
	include/pmc/pmc_fixedintegerarray.h

src/call/context_accessors$(O): $(PARROT_H_HEADERS) \
	src/call/context_accessors.c

src/call/pcc$(O) : $(INC_DIR)/oplib/ops.h \
	$(PARROT_H_HEADERS) \
	$(INC_DIR)/runcore_api.h \
	src/call/pcc.c \
	src/call/pcc.str \
	include/pmc/pmc_key.h include/pmc/pmc_continuation.h

src/call/context$(O) : $(PARROT_H_HEADERS) \
	include/pmc/pmc_sub.h src/call/context.c

src/interp/inter_cb$(O) : $(PARROT_H_HEADERS) \
	include/pmc/pmc_parrotinterpreter.h \
	src/interp/inter_cb.str src/interp/inter_cb.c

src/interp/inter_misc$(O) : $(PARROT_H_HEADERS) \
	src/interp/inter_misc.c \
	src/interp/inter_misc.str \
	compilers/imcc/imc.h \
	compilers/imcc/cfg.h \
	compilers/imcc/debug.h \
	compilers/imcc/instructions.h \
	compilers/imcc/sets.h \
	compilers/imcc/symreg.h \
	compilers/imcc/unit.h \
	$(INC_DIR)/oplib/ops.h \
	$(INC_DIR)/runcore_api.h

src/interp/inter_create$(O) : $(PARROT_H_HEADERS) \
	$(INC_DIR)/oplib/core_ops.h \
	src/gc/gc_private.h \
	src/interp/inter_create.c \
	src/interp/inter_create.str \
	compilers/imcc/imc.h \
	compilers/imcc/cfg.h \
	compilers/imcc/debug.h \
	compilers/imcc/instructions.h \
	compilers/imcc/sets.h \
	compilers/imcc/symreg.h \
	compilers/imcc/unit.h \
	$(INC_DIR)/oplib/ops.h \
	$(INC_DIR)/runcore_api.h

src/call/ops$(O) : $(INC_DIR)/oplib/ops.h \
	$(PARROT_H_HEADERS) include/pmc/pmc_continuation.h \
	$(INC_DIR)/runcore_api.h src/call/ops.c

src/io/api$(O) : $(PARROT_H_HEADERS) src/io/io_private.h \
	src/io/api.c \
	src/io/api.str include/pmc/pmc_filehandle.h \
	include/pmc/pmc_stringhandle.h \
	$(INC_DIR)/extend.h \
	$(INC_DIR)/extend_vtable.h

src/io/buffer$(O) : $(PARROT_H_HEADERS) src/io/io_private.h src/io/buffer.c

src/io/portable$(O) : $(PARROT_H_HEADERS) src/io/io_private.h src/io/portable.c

src/io/unix$(O) : $(PARROT_H_HEADERS) src/io/io_private.h \
    include/pmc/pmc_filehandle.h src/io/unix.c

src/io/utf8$(O) : $(PARROT_H_HEADERS) src/io/io_private.h src/string/unicode.h \
    src/io/utf8.c

src/io/win32$(O) : $(PARROT_H_HEADERS) src/io/io_private.h \
    include/pmc/pmc_filehandle.h src/io/win32.c

src/gc/alloc_memory$(O) : $(PARROT_H_HEADERS) src/gc/alloc_memory.c

src/main$(O) : $(INC_DIR)/imcc.h $(PARROT_H_HEADERS) \
	$(INC_DIR)/embed.h $(INC_DIR)/runcore_api.h src/gc/gc_private.h \
	src/main.c

src/multidispatch$(O) : \
	src/multidispatch.c \
	src/multidispatch.str \
	$(INC_DIR)/oplib/ops.h $(PARROT_H_HEADERS) \
	include/pmc/pmc_nci.h include/pmc/pmc_sub.h

src/packfile$(O) : src/packfile.str \
	src/packfile.c \
	include/pmc/pmc_sub.h include/pmc/pmc_key.h \
	compilers/imcc/imc.h \
	compilers/imcc/cfg.h \
	compilers/imcc/debug.h \
	compilers/imcc/instructions.h \
	compilers/imcc/sets.h \
	compilers/imcc/symreg.h \
	compilers/imcc/unit.h \
	$(INC_DIR)/oplib/ops.h \
	$(INC_DIR)/embed.h $(INC_DIR)/extend.h $(INC_DIR)/extend_vtable.h \
	$(PARROT_H_HEADERS) $(INC_DIR)/runcore_api.h

src/packfile/pf_items$(O) : $(PARROT_H_HEADERS) src/packfile/pf_items.c

src/packout$(O) : $(PARROT_H_HEADERS) include/pmc/pmc_key.h src/packout.c

src/parrot$(O) : $(GENERAL_H_FILES)

src/runcore/cores$(O) : src/runcore/cores.str \
	src/runcore/cores.c \
	include/pmc/pmc_sub.h \
	$(INC_DIR)/dynext.h $(INC_DIR)/embed.h $(INC_DIR)/oplib/core_ops.h \
	$(INC_DIR)/oplib/ops.h \
	$(INC_DIR)/runcore_api.h $(INC_DIR)/runcore_trace.h \
	$(PARROT_H_HEADERS)

src/embed$(O) : $(PARROT_H_HEADERS) $(INC_DIR)/embed.h \
        src/embed.c src/embed.str \
        $(INC_DIR)/oplib/ops.h $(INC_DIR)/runcore_api.h \
        compilers/imcc/imc.h \
        compilers/imcc/cfg.h \
        compilers/imcc/debug.h \
        compilers/imcc/instructions.h \
        compilers/imcc/sets.h \
        compilers/imcc/symreg.h \
        compilers/imcc/unit.h \
		include/pmc/pmc_sub.h

src/dataypes$(O) : $(GENERAL_H_FILES) src/dataypes.c

src/exit$(O) : $(PARROT_H_HEADERS) src/exit.c

src/nci/api$(O) : src/nci/api.str \
	src/nci/api.c \
	$(PARROT_H_HEADERS)

src/nci/core_thunks$(O) : src/nci/core_thunks.c \
	$(PARROT_H_HEADERS) \
	include/pmc/pmc_nci.h

## SUFFIX OVERRIDE
src/nci/extra_thunks$(O) : \
    $(PARROT_H_HEADERS) \
    include/pmc/pmc_nci.h \
    src/nci/extra_thunks.c
	$(CC) $(CFLAGS) @optimize::src/nci/extra_thunks.c@ @ccwarn::src/nci/extra_thunks.c@ @cc_shared@ -I$(@D) @cc_o_out@$@ -c src/nci/extra_thunks.c

src/vtables$(O) : $(PARROT_H_HEADERS) src/vtables.c

## SUFFIX OVERRIDE
src/gc/system$(O) : $(PARROT_H_HEADERS)  src/gc/gc_private.h src/gc/system.c
	$(CC) $(CFLAGS) @optimize::src/gc/system.c@ @ccwarn::src/gc/system.c@ @cc_shared@ -I$(@D) @cc_o_out@$@ -c src/gc/system.c

src/gc/gc_private.h : $(INC_DIR)/settings.h

src/gc/malloc$(O) : src/gc/malloc.c

src/warnings$(O) : $(PARROT_H_HEADERS) src/warnings.c

src/misc$(O) : $(PARROT_H_HEADERS) src/misc.c

src/utils$(O) : $(PARROT_H_HEADERS) include/pmc/pmc_nci.h src/utils.c

## SUFFIX OVERRIDE
src/spf_render$(O) : $(PARROT_H_HEADERS) src/spf_render.str src/spf_render.c
	$(CC) $(CFLAGS) @optimize::src/spf_render.c@ @ccwarn::src/spf_render.c@ @cc_shared@ -I$(@D) @cc_o_out@$@ -c src/spf_render.c

src/spf_vtable$(O) : $(PARROT_H_HEADERS) src/spf_vtable.str src/spf_vtable.c

src/string/encoding$(O) : $(PARROT_H_HEADERS) src/string/encoding.c

src/string/charset$(O) : $(PARROT_H_HEADERS) src/string/charset.c \
	src/string/encoding/fixed_8.h \
	src/string/encoding/utf8.h \
	src/string/encoding/utf16.h \
	src/string/encoding/ucs2.h \
	src/string/encoding/ucs4.h \
	src/string/charset/ascii.h \
	src/string/charset/binary.h \
	src/string/charset/iso-8859-1.h \
	src/string/charset/unicode.h

src/pbc_merge$(O) : $(INC_DIR)/embed.h src/pbc_merge.c \
	include/pmc/pmc_sub.h $(INC_DIR)/oplib/ops.h $(PARROT_H_HEADERS)

src/io/filehandle$(O) : $(PARROT_H_HEADERS) include/pmc/pmc_filehandle.h \
    src/io/io_private.h src/io/filehandle.c

src/gc/malloc_trace$(O) : src/gc/malloc.c src/gc/malloc_trace.c

src/packfile/pf_items$(O) : $(PARROT_H_HEADERS) src/packfile/pf_items.c

src/atomic/gcc_x86$(O) : $(PARROT_H_HEADERS) $(INC_DIR)/atomic/gcc_x86.h \
    src/atomic/gcc_x86.c

# core_ops depends upon config.h so that it gets updated along with
# updates to config.h's version numbers
src/ops/core_ops$(O) : src/ops/core_ops.c \
    $(PARROT_H_HEADERS) \
    include/parrot/dynext.h \
    include/parrot/embed.h \
    include/parrot/oplib/core_ops.h \
    include/parrot/runcore_api.h \
    include/pmc/pmc_continuation.h \
    include/pmc/pmc_parrotlibrary.h \
    src/io/io_private.h

@TEMP_gc_c@

@TEMP_pmc_build@

@TEMP_charset_build@

@TEMP_encoding_build@

# $(CONFIGURE_GENERATED_FILES) : Configure.pl
#	$(PERL) Configure.pl

$(INC_DIR)/vtable.h : src/vtable.tbl $(BUILD_TOOLS_DIR)/vtable_h.pl lib/Parrot/Vtable.pm
	$(PERL) $(BUILD_TOOLS_DIR)/vtable_h.pl

###############################################################################
#
# Documentation targets:
#
###############################################################################

#IF(has_perldoc):docs : docs.dummy
#ELSE:docs : docs.stub

docs.stub:
	@echo "Perldoc is required, but not detected."

docs.dummy :
	$(MAKE) docs

docs-clean :
	$(MAKE) docs clean

#IF(has_perldoc):html : html.dummy
#ELSE:html : html.stub

html.stub:
	@echo "Perldoc is required, but not detected."

html.dummy :
	$(MAKE) docs html

html-clean :
	$(MAKE) docs html-clean

#IF(has_perldoc):htmlhelp : htmlhelp.dummy
#ELSE:htmlhelp : htmlhelp.stub

htmlhelp.stub:
	@echo "Perldoc is required, but not detected."

htmlhelp.dummy :
	$(MAKE) docs htmlhelp

htmlhelp-clean :
	$(MAKE) docs htmlhelp-clean

pdf:
	$(MAKE) docs pdf

pdf-clean:
	$(MAKE) docs pdf-clean

###############################################################################
#
# compiler implementation targets:
#
###############################################################################

ext-clean:
	$(RM_RF) $(NQPRX_LIB_PBCS) $(NQPRX_LIB_SETTING) parrot-nqp*

###############################################################################
#
# editors targets:
#
###############################################################################

editor-clean :
	$(MAKE) editor clean

###############################################################################
#
# Testing Targets:
#
###############################################################################

# The --running-make-test argument is currently used by long-running tests
# to disable GC_DEBUG.
EXTRA_TEST_ARGS = --gc-debug
DISTRO_TEST_FILES = \
    t/distro/*.t
BENCHMARK_TEST_FILES = \
    t/benchmark/*.t
PERL_TEST_FILES = \
    t/perl/*.t
CODINGSTD_TEST_FILES = \
    t/codingstd/*.t
RUN_TEST_FILES = \
    t/run/*.t
RUNCORE_TEST_FILES = \
    --runcore-tests
SRC_TEST_FILES = \
    t/src/*.t
TOOLS_TEST_FILES = \
    t/tools/*.t
LIBRARY_TEST_FILES = @library_tests@
PMC2CUTILS_DIR = t/tools/pmc2cutils
HARNESS_DIR = t/pharness
BUILDTOOLS_TEST_FILES = \
    $(PMC2CUTILS_DIR)/*.t \
    $(HARNESS_DIR)/*.t
MANIFEST_DIR = t/manifest
INSTALL_TOOLS_DIR = t/tools/install
MANIFEST_TEST_FILES = \
    $(MANIFEST_DIR)/*.t \
    $(INSTALL_TOOLS_DIR)/*.t
EXAMPLES_TEST_FILES = \
    t/examples/*.t
CONFIGURE_TEST_FILES = \
    t/configure/*.t \
    t/steps/*.t

# Common prep for all test targets.
# We probably need a complete build before running the tests.
test_prep : all

# Run test cases with a single call of t/harness. Users have to look at only
# one report. The default set of tests to run is contained in t/harness,
# make any edits there. Some tests are run in a separate harness only because
# integrating them in a single run is difficult.

# Normal test package
test : test_core

# Test Parrot core.
test_core: test_prep
	$(PERL) t/harness $(EXTRA_TEST_ARGS)

# run the test suite, create a TAP archive and send it off to smolder
smolder_test : test_prep
	$(PERL) t/harness $(EXTRA_TEST_ARGS) --archive --send-to-smolder

smolder_coretest : corevm
	$(PERL) t/harness $(EXTRA_TEST_ARGS) --core-tests --archive --send-to-smolder

smoke : smolder_test

# "core tests" -- test basic functionality but not ancillaries
coretest : corevm
	$(PERL) t/harness $(EXTRA_TEST_ARGS) --core-tests

# automake compatibility
check : test

# Test various run cores and other stuff
# 'testg' and 'testj' are tested only
# when the needed runcores are available
fulltest :
	-@make@ testb \
	testf \
	testr \
	src_tests \
	run_tests \
	buildtools_tests \
	perl_tests \
	library_tests \
	codetest \
	benchmark_tests \
	manifest_tests \
	examples_tests \
	distro_tests

# bounds checking, slow core
testb : test_prep
	$(PERL) t/harness $(EXTRA_TEST_ARGS) -b $(RUNCORE_TEST_FILES)

# fast core
testf : test_prep
	$(PERL) t/harness $(EXTRA_TEST_ARGS) -f $(RUNCORE_TEST_FILES)

# Computed goto
testg : test_prep
	$(PERL) t/harness $(EXTRA_TEST_ARGS) -g $(RUNCORE_TEST_FILES)

# gcdebug core
testgcd : test_prep
	$(PERL) t/harness $(EXTRA_TEST_ARGS) -G $(RUNCORE_TEST_FILES)

# JIT core - target retained, but falls back to standard core
testj : test_prep
	$(PERL) t/harness $(EXTRA_TEST_ARGS) $(RUNCORE_TEST_FILES)

# normal core, write and run Parrot Byte Code
testr : test_prep
	$(PERL) t/harness $(EXTRA_TEST_ARGS) -r $(RUNCORE_TEST_FILES)

# normal core, write and run PASM
testp : test_prep
	$(PERL) t/harness $(EXTRA_TEST_ARGS) -r $(RUNCORE_TEST_FILES)

# normal core, optimization level 1
testO1 : test_prep
	$(PERL) t/harness $(EXTRA_TEST_ARGS) -O1 $(RUNCORE_TEST_FILES)

# test the EXEC stuff
testexec: test_prep
	$(PERL) t/harness $(EXTRA_TEST_ARGS) --run-exec $(RUNCORE_TEST_FILES)

# Test that need to be compiled by the C-compiler
src_tests :
	$(PERL) t/harness $(SRC_TEST_FILES)

# Command line and various environments
run_tests :
	$(PERL) t/harness $(RUN_TEST_FILES)

# Test the Perl5 Modules in the Parrot distribution
perl_tests :
	$(PERL) t/harness $(PERL_TEST_FILES)

codetest :
	$(PERL) t/harness $(EXTRA_TEST_ARGS) --code-tests

# Test pdd07_codingstd
codingstd_tests :
	$(PERL) t/harness $(CODINGSTD_TEST_FILES)

# Run standard test suite with warnings enabled.
warnings_tests:
	$(PERL) t/harness $(EXTRA_TEST_ARGS) -w $(RUNCORE_TEST_FILES)

buildtools_tests : corevm
	$(PERL) t/harness $(BUILDTOOLS_TEST_FILES)

manifest_tests :
	$(PERL) t/harness $(MANIFEST_TEST_FILES)

examples_tests : test_prep
	$(PERL) t/harness $(EXAMPLES_TEST_FILES)

# benchmark tests
benchmark_tests : test_prep
	$(PERL) t/harness $(BENCHMARK_TEST_FILES)

# Running a benchmark
mopsbench : test_prep
	$(PARROT) examples/benchmarks/mops_intval.pasm

# distro tests
distro_tests : test_prep
	$(PERL) t/harness $(DISTRO_TEST_FILES)

# configure tests
configure_tests :
	$(PERL) t/harness $(CONFIGURE_TEST_FILES)

# library tests - tests run by make test but not by make fulltest or make cover
library_tests : test_prep
	$(PERL) t/harness $(EXTRA_TEST_ARGS) $(LIBRARY_TEST_FILES)

###############################################################################
#
# Cleaning Targets:
#
###############################################################################

clean : \
    test-clean \
    prog-clean \
    dynext-clean \
#IF(has_perldoc):    docs-clean \
#IF(has_perldoc):    html-clean \
    examples-clean \
    ext-clean \
#UNLESS(win32):    cover-clean \
    editor-clean
	$(RM_F) chartypes "*.s" "*~"
	$(RM_F) $(FLUID_FILES_1)
	$(RM_F) $(FLUID_FILES_2)
	$(RM_RF) lib/Parrot/OpLib
	$(RM_RF) runtime/parrot/languages/data_json
	$(RM_F) $(NQP_CLEANUPS) $(PGE_CLEANUPS) $(TGE_CLEANUPS)
	$(RM_F) $(PIRC_CLEANUPS) $(PCT_CLEANUPS) $(DATA_JSON_CLEANUPS)
	$(RM_F) $(DYNOPLIBS_CLEANUPS) $(DYNPMC_CLEANUPS)
	$(RM_F) $(GEN_PASM_INCLUDES) $(GEN_PM_INCLUDES)
	$(RM_F) $(NQPRX_CLEANUPS)  $(OPSC_CLEANUPS)

prog-clean :
	$(RM_F) \
    $(O_FILES) \
    $(PARROT) \
    $(MINIPARROT) \
    $(LIBPARROT) \
    $(INSTALLABLEOPS2C) \
    $(INSTALLABLEPARROT) \
    $(INSTALLABLEDIS) \
    $(INSTALLABLEPDUMP) \
    $(INSTALLABLEPBC_MERGE) \
    $(INSTALLABLEPBCTOEXE) \
    $(INSTALLABLEPDB) \
    $(INSTALLABLECONFIG) \
    $(INSTALLABLENQP) \
    $(INSTALLABLENCITHUNKGEN) \
    $(INSTALLABLEPROVE) \
    pbc_to_exe.pbc pbc_to_exe.c pbc_to_exe$(O) pbc_to_exe$(EXE) \
    $(NCI_THUNK_GEN) parrot_nci_thunk_gen.c parrot_nci_thunk_gen$(O) parrot_nci_thunk_gen.pbc \
    ops2c.pbc ops2c.c ops2c$(O) ops2c$(EXE) ops2c.pir \
    parrot-prove.pbc parrot-prove.c parrot-prove$(O) parrot-prove$(EXE) \
    parrot_config$(EXE) parrot_config.c parrot_config$(O) parrot_config.pbc \
    compilers/imcc/main$(O) \
    $(PDUMP) src/pbc_dump$(O) src/packdump$(O) \
    $(PDB) src/parrot_debugger$(O) \
    $(PBC_MERGE) src/pbc_merge$(O) \
    $(DIS) src/pbc_disassemble$(O)
	$(RM_F) \
    src/main$(O) \
    src/null_config$(O) \
    src/parrot_config$(O) \
    src/install_config$(O) \
    src/nci_test$(O) \
    $(LIBNCI_TEST_SO) \
    src/glut_callbacks$(O) \
    src/glut_nci_thunks$(O) \
    $(LIBGLUTCB_SO) \
    src/extra_nci_thunks$(O) \
    $(EXTRANCITHUNKS_SO) \
    install_config.fpmc
	$(PERL) $(BUILD_TOOLS_DIR)/c2str.pl --init
	$(RM_F) \
    $(STR_FILES) \
    src/string/private_cstring.h "src/pmc/*.c" "include/pmc/pmc_*.h" \
    "src/pmc/*.dump" vtable.dump "*.def" "*.lib" "*.exp"

archclean: dynext-clean
	$(RM_F) \
    $(O_FILES) \
    $(GEN_CONFIGS) \
    $(GEN_MAKEFILES) \
    $(PARROT) \
    $(MINIPARROT) \
    $(INSTALLABLEPARROT) \
    $(INSTALLABLEDIS) \
    $(INSTALLABLEPDUMP) \
    $(INSTALLABLEPBC_MERGE) \
    $(INSTALLABLEPDB) \
    $(INSTALLABLECONFIG) \
    $(INSTALLABLENQP) \
    compilers/imcc/main$(O) \
    $(PDUMP) src/pbc_dump$(O) src/packdump$(O) \
    $(PDB) src/parrot_debugger$(O) \
    $(PBC_MERGE) src/pbc_merge$(O) \
    $(DIS) src/pbc_disassemble$(O) \
    $(PARROT_CONFIG) parrot_config$(O) parrot_config.c \
    src/parrot_config$(O) parrot_config.pbc \
    pbc_to_exe$(EXE) pbc_to_exe$(O) pbc_to_exe.pbc \
    src/null_config$(O) \
    src/parrot_config$(O) \
    src/install_config$(O) \
    install_config.fpmc \
    src/nci_test$(O) \
    $(LIBNCI_TEST_SO) \
    src/glut_callbacks$(O) \
    $(LIBGLUTCB_SO) \
    src/extra_nci_thunks$(O) \
    $(EXTRANCITHUNKS_SO) \
    $(LIBPARROT_STATIC) \
    $(LIBPARROT_SHARED)

dynext-clean :
# shared libs (LOAD_EXT, SHARE_EXT)
# win32 import library (.lib - shared object is deleted by LIBNCI_TEST_SO above)
# win32 program data base - contains debugging info (.pdb)
# win32 incremental link status files (.ilk)
# win32 exported functions and data items (.exp)
# win32 export definition files (.def)
	$(RM_F) \
    "$(DYNEXT_DIR)/*$(LOAD_EXT)" \
    "$(DYNEXT_DIR)/*$(SHARE_EXT)" \
    "$(DYNEXT_DIR)/*.lib" \
    "*.pdb" "$(DYNEXT_DIR)/*.pdb" \
    "*.ilk" "$(DYNEXT_DIR)/*.ilk" \
    "*.exp" "$(DYNEXT_DIR)/*.exp" \
    "*.def" "$(DYNEXT_DIR)/*.def" \
    "*.manifest" "$(DYNEXT_DIR)/*.manifest"

# Remove files generated by the test suite
# XXX Is there a danger of too long command lines in the $(RM_F) commands,
# or is there an automatic xargs?
test-clean :
	$(RM_F) t/compilers/data_json/*.pir
	$(RM_F) t/compilers/imcc/imcpasm/*.pir
	$(RM_F) t/compilers/imcc/syn/*.pir t/compilers/imcc/syn/*.pasm
	$(RM_F) t/compilers/imcc/reg/*.pir t/compilers/imcc/reg/*.pasm
	$(RM_F) t/compilers/pct/*.pir
	$(RM_F) t/compilers/pge/perl6regex/*.pir
	$(RM_F) t/compilers/pge/*.pir
	$(RM_F) t/compilers/tge/*.pir
	$(RM_F) \
    "t/*/*$(O)" \
    "t/*/*.out" \
    "t/*/*.pasm" \
    "t/*/*_pbcexe*" \
    "t/*/*.pir" \
    "t/*/*.stabs.s"
	$(RM_F) \
    "t/library/*.pbc" \
    "t/dynoplibs/*.pbc" \
    "t/op/*.pbc" \
    "t/oo/*.pbc" \
    "t/pmc/*.pbc" \
    "t/dynpmc/*.pbc" \
    "t/stress/*.pbc" \
    "t/tools/*.pbc"
	$(RM_F) \
    "t/src/*.c" \
    "t/src/*.pdb" \
    "t/src/*.manifest"
	$(RM_F) \
     "t/tools/pmc2c.t_*" \
     "t/tools/pmc2c.pmc_t_*" \
     "t/tools/parrot_debugger.t.*"
	$(RM_F) \
     "test$(EXE)" \
     "test.*"
	$(RM_F) \
     "parrot_test_run.tar.gz" \
	 ".pod_examinable*.sto"

# a failing step of cleaning, usually doesn't concern the following steps
realclean : clean
	$(RM_RF) \
    $(CONFIGURE_GENERATED_FILES) \
    blib \
    cover_db

distclean : realclean

# Require .svn to exist first
# Otherwise it'll remove every last file
svnclobber : .svn
	$(PERL) tools/dev/svnclobber.pl

reconfig : realclean
	$(PERL) Configure.pl $(CONFIG_ARGS)

manitest :
	$(PERL) tools/dev/manicheck.pl

opsrenumber :
	$(PERL) tools/dev/opsrenumber.pl $(OPS_FILES)

pmcrenumber :
	$(PERL) tools/dev/pmcrenumber.pl src/pmc/pmc.num

###############################################################################
#
# SVN Targets:
#
###############################################################################

update :
	svn -q update

status :
	svn -q status

patch :
	svn diff

LINTABLE_CFILES = `echo src/main$(O) $(O_FILES) src/parrot_config$(O) | $(PERL) -pe @PQ@s/\.o/\.c/g@PQ@`

lint : sunlint

SUNLINT = lint

# This target does sneaky magic to get the $(NOTE) fields to work.  It's
# doing replaces in $(NOTE), which is empty, of strings that will never match.
NOTE =
SUNLINT_HUSH_OPTS = \
    $(NOTE:% Errors that will never be silenced, and we must always hush =%)\
    -erroff=E_ARGUMENT_CONVERT          $(NOTE:% implicit integer-to-long conversion =%) \
    -erroff=E_BAD_PTR_CAST                    $(NOTE:% pointer casts may be troublesome =%) \
    -erroff=E_BAD_PTR_CAST_ALIGN          $(NOTE:% alignment problems with cast =%) \
    -erroff=E_LABEL_NOT_USED          $(NOTE:% Unused label =%) \
    -erroff=E_CONSTANT_CONDITION          $(NOTE:% Constant condition =%) \
    -erroff=E_INCL_NUSD                    $(NOTE:% An include file was unused =%) \
    -erroff=E_INDISTING_FROM_TRUNC          $(NOTE:% Identifier will be ambiguous if truncated =%) \
    -erroff=E_MCR_NODIFF                    $(NOTE:% Macros differ between source files =%) \
    -erroff=E_INIT_DOES_NOT_FIT          $(NOTE:% initializer does not fit or is out of range+ 0xf0e69739 =%) \
    -erroff=E_NONPORT_SBITWISE_OP   $(NOTE:% bitwise operations on signed values not portable =%) \
    \
    $(NOTE:% Things to drop some day =%) \
    -erroff=E_FUNC_ARG_UNUSED          $(NOTE:% Unused function argument =%) \
    -erroff=E_STMT_NOT_REACHED          $(NOTE:% Unreachable statement =%) \
    -erroff=E_NOP_IF_STMT                    $(NOTE:% if has a no-op =%) \
    -erroff=E_NOP_ELSE_STMT                    $(NOTE:% else has a no-op =%) \
    -erroff=E_CASE_FALLTHRU                    $(NOTE:% case fallthru =%) \
    -erroff=E_STATIC_UNUSED                    $(NOTE:% Static function not used =%) \

SUNLINT_OPTS_FOR_THE_FUTURE = -b -m -Xc

# Lint options at: http:////docs.sun.com//app//docs//doc//819-5265//6n7c29cli?a=view
SUNLINTOPTS = \
    -b \
    -p \
    -fd \
    -Ncheck=%all \
    -Nlevel=4 \
    -errchk=%all \
    -errhdr=%user \
    -errtags \
    -errchk=no%longptr64 \
    -errfmt=simple \
    $(SUNLINT_HUSH_OPTS) \

sunlint :
	rm -f *.ln
	$(SUNLINT) $(CC_INC) "-Iinclude/pmc" $(SUNLINTOPTS) $(LINTABLE_CFILES)

BSD_LINT_FLAGS = -a -aa -b -c -e -h -n -p -r -u -x -z -F -H -V

# 132: conversion from '...' may lose accuracy
# 135: possible pointer alignment problem
# 236: static function unused
# 241: dubious operation on enum
# 247: pointer casts may be troublesome
# 249: syntax error (huh? this appears in atomic/gcc_x86.h but doesn't
#      cause any compiler to barf)
# 259: conversion to '...' due to prototype
# 265: ANSI C does not support 'long long'
# 277: initialisation of '...' with '...'
# 278: combination of '...' and '...', arg #...
BSD_LINT_EXCLUSIONS = -X132,135,236,241,247,249,259,265,277,278

bsdlint : $(PARROT)
	rm -f *.ln
	$(LINT) $(CC_INC) "-Iinclude/pmc" $(BSD_LINT_FLAGS) $(BSD_LINT_EXCLUSIONS) $(LINTABLE_CFILES)

# For checking with splint see also
# http:////trac.parrot.org/parrot/wiki/splint
# Splint: http:////splint.org
SPLINT = splint

# Temp directory for splint.  Add +keep to splintflags if you want work files
# kept in there after completion.
SPLINT_TMP = $(TEMPDIR)/splint

# Splint flags: http://splint.org/manual/html/appB.html
# The dashes in the names don't make any difference to Splint, but I've
# made them match how they are in the manual.  Otherwise, you might be
# looking for "declundef", except that it's "decl-undef" in the docs.
SPLINTFLAGS_BASE = \
    +standard \
    -hints \
    \
    +indentspaces 4 \
    +locindentspaces 4 \
    +linelen 120 \
    -message-stream-stdout \
    +showdeephistory \
    -showfunc \
    -tmpdir $(SPLINT_TMP) \
    \
    +posix-lib \
    -skip-posix-headers \
    \
    +ansi89-limits \
    +num-struct-fields 255 \
    \
    -show-summary \
    +show-scan \
    +time-dist \
    \
    +cpp-names \
    +ansi-reserved \
    +ansi-reserved-internal \
    -iso-reserved \
    -iso-reserved-internal \
    -include-nest 10 \

# Memory safety checks
# Transfer errors (-mem-trans) are too tough for us right now
SPLINTFLAGS_MEMORY_SAFETY = \
    +bufferoverflow \
    +bufferoverflowhigh \
    +read-only-strings \
    +read-only-trans \
    +strict-destroy \
    +strict-use-released \
    +use-released \
    -must-free \
    -mustfreefresh \
    -mustfreeonly \
    +null \
    +nullptrarith \
    +nullret \
    -ptr-arith \
    +ptr-negate \
    -zero-ptr \
    -mem-trans

# Macro safety checks
SPLINTFLAGS_MACRO_SAFETY = \
    +macro-assign \
    +macro-empty \
    +macro-parens \
    +macro-redef \
    +macro-stmt \
    +macro-unrecog \

# Watch for unsafe comparisons
SPLINTFLAGS_UNSAFE_COMPARISONS = \
    +bool-compare \
    +ptr-compare \
    +real-compare \
    +unsigned-compare

# But allow us some slop in boolean comparisons
SPLINTFLAGS_BOOLEAN_SLOP = \
    -pred-bool-int \
    -pred-bool-ptr \
    -pred-bool-others \
    -boolops \

# const and other qualifiers
# Report qualifier mismatches only if dangerous (+relax-quals)
SPLINTFLAGS_QUALIFIERS = \
    +relax-quals

# Symbol definitions
SPLINTFLAGS_SYMBOL_DEFINITIONS = \
    +decl-undef \
    +incon-defs \
    +incon-defs-lib \

# Format codes
SPLINTFLAGS_FORMAT = \
    +format-code \
    +format-type \

# Problems with evaluation and control structions
SPLINTFLAGS_EVALUATION = \
    +controlnestdepth 15 \
    +duplicate-quals \
    +eval-order \
    +eval-order-uncon \

# Types and stuff
SPLINTFLAGS_TYPES = \
    +char-index \
    +char-int \
    +enum-members \
    +ignore-signs \
    +long-integral \
    +match-any-integral \

# Other options we'd like to add back
# +initallelements : Right now, the *.ops files don't initialize all
#  values of the arrays
# +casebreak: Auto-generated ops have way too case fallthrus right now
# +fcnuse: We have many functions that are defined but not used, but they
#  should get hidden or ifdeffed
# +redef, +redecl: Ops currently have tons of redefinitions

# added to splint target to simplify experimentation,
# example: make SPLINTFLAGS_TEST='-posixstrictlib +posixlib' splint

SPLINTFLAGS_TEST =

SPLINTFLAGS = \
	$(SPLINTFLAGS_BASE) \
	$(SPLINTFLAGS_MEMORY_SAFETY) \
	$(SPLINTFLAGS_MACRO_SAFETY) \
	$(SPLINTFLAGS_UNSAFE_COMPARISONS) \
	$(SPLINTFLAGS_BOOLEAN_SLOP) \
	$(SPLINTFLAGS_QUALIFIERS) \
	$(SPLINTFLAGS_SYMBOL_DEFINITIONS) \
	$(SPLINTFLAGS_FORMAT) \
	$(SPLINTFLAGS_EVALUATION) \
	$(SPLINTFLAGS_TYPES) \

SPLINT_SOURCE = `echo $(O_FILES) | $(PERL) -pe @PQ@s/\.o/\.c/g@PQ@`

splint-all : $(PARROT)
	$(MKPATH) $(SPLINT_TMP)
	$(SPLINT) $(CC_INC) "-Iinclude/pmc" "-Icompilers/ast" $(SPLINTFLAGS) \
	$(SPLINT_SOURCE) \
	$(SPLINT) $(CC_INC) $(SPLINTFLAGS) compilers/imcc/main.c

# "splint" is the less-thorough splint target.  For cage cleaning work,
# you'll probably want to specify SPLINT_SOURCE rather than work on the
# entire tree, like so:
#     make splint SPLINT_SOURCE='src/call/*.c'

splint : all
	$(MKPATH) $(SPLINT_TMP)
	$(SPLINT) $(CC_INC) "-Iinclude/pmc" "-Icompilers/ast" $(SPLINTFLAGS) \
	+partial -DNDEBUG \
	$(SPLINT_SOURCE) \
		| grep -v 'Source code error generation point'

COVER_FLAGS = -fprofile-arcs -ftest-coverage
COVER_DIRS = \
    src \
    src/call \
    src/dynoplibs \
    src/dynpmc \
    src/gc \
    src/interp \
    src/ops \
    src/packfile \
    src/pmc \
    src/runcore \
    src/string \
    src/string/charset \
    src/string/encoding \
    $(BUILD_DIR) \
    $(BUILD_DIR)/t/perl \
    src/io \
    compilers/imcc

cover: \
    cover.dummy \
    cover-testb \
    cover-testf \
    cover-testr \
    cover-src \
    cover-run \
    cover-perl \
    cover-extra \
    cover-codingstd \
    cover-benchmark \
    cover-manifest \
    cover-examples \
    cover-distro
	build_dir=$$PWD; \
    for dir in $(COVER_DIRS); \
    do \
	cd $$dir; \
	gcov *.c; \
	cd $$build_dir; \
	gcov2perl $$dir/*.gcov; \
    done
	cover -ignore_re '^\/usr\/local\/bin'

cover.dummy:
	$(PERL) Configure.pl --ccflags="$(CC_FLAGS) $(COVER_FLAGS)" \
    --linkflags="$(COVER_FLAGS)" --ldflags="$(COVER_FLAGS)"

cover-testb: cover.dummy
	-@make@ testb

cover-testf: cover.dummy
	-@make@ testf

cover-testg: cover.dummy
	-@make@ testg

cover-testj: cover.dummy
	-@make@ testj

cover-testr: cover.dummy
	-@make@ testr

cover-src: cover.dummy
	-@make@ src_tests

cover-run: cover.dummy
	-@make@ run_tests

cover-perl: cover.dummy
	-@make@ perl_tests

cover-extra: cover.dummy
	-@make@ library_tests

cover-codingstd: cover.dummy
	-@make@ codingstd_tests

cover-benchmark: cover.dummy
	-@make@ benchmark_tests

cover-manifest: cover.dummy
	-@make@ manifest_tests

cover-examples: cover.dummy
	-@make@ examples_tests

cover-distro: cover.dummy
	-@make@ distro_tests

cover-clean:
	$(PERL) -MCwd -e 'for my $$dir qw ( $(COVER_DIRS) ) {my $$cwd = cwd(); chdir $$dir; print "Deleting gcov-generated files in $$dir\n"; unlink glob( "*.gcda *.gcno *.gcov" ); chdir $$cwd;}'

###############################################################################
#
# installation
#
###############################################################################

install: install-bin install-dev-only
install-dev: install

install-bin: installable
	$(PERL) tools/dev/install_files.pl \
    --buildprefix=$(BUILDPREFIX) \
    --prefix=$(PREFIX) \
    --exec-prefix=$(EXEC_PREFIX) \
    --bindir=$(BIN_DIR) \
    --libdir=$(LIB_DIR) \
    --includedir=$(INCLUDE_DIR) \
    --destdir=$(DESTDIR) \
    --docdir=$(DOC_DIR) \
    --versiondir=$(VERSION_DIR) \
    --pkgconfigdir=@PKGCONFIG_DIR@ \
    MANIFEST MANIFEST.generated

install-dev-only: installable
	$(PERL) tools/dev/install_dev_files.pl \
    --buildprefix=$(BUILDPREFIX) \
    --prefix=$(PREFIX) \
    --exec-prefix=$(EXEC_PREFIX) \
    --bindir=$(BIN_DIR) \
    --libdir=$(LIB_DIR) \
    --includedir=$(INCLUDE_DIR) \
    --destdir=$(DESTDIR) \
    --docdir=$(DOC_DIR) \
    --datadir=$(DATA_DIR) \
    --srcdir=@srcdir@ \
    --versiondir=$(VERSION_DIR) \
    MANIFEST MANIFEST.generated

install-doc:
	$(PERL) tools/dev/install_doc_files.pl \
    --buildprefix=$(BUILDPREFIX) \
    --prefix=$(PREFIX) \
    --docdir=$(DOC_DIR) \
    --destdir=$(DESTDIR) \
    --versiondir=$(VERSION_DIR) \
    MANIFEST MANIFEST.generated

###############################################################################
#
# release targets
#
###############################################################################

release : MANIFEST MANIFEST.generated
	[ -d parrot-$(VERSION) ] || ln -s . parrot-$(VERSION)
	@$(RM_F) MANIFEST.real
	mv MANIFEST MANIFEST.real
	grep -v DEVELOPING MANIFEST.real > MANIFEST
	$(PERL) -lane 'print"parrot-$(VERSION)/$$F[0]"unless!length||/#/' MANIFEST | \
    tar -zcv -T - -f parrot-$(VERSION).tar.gz
	$(PERL) -lane 'print"parrot-$(VERSION)/$$F[0]"unless!length||/#/' \
	     MANIFEST | tar -jcv -T - -f parrot-$(VERSION).tar.bz2
	sha256sum parrot-$(VERSION).tar.gz > parrot-$(VERSION).tar.gz.sha256
	sha256sum parrot-$(VERSION).tar.bz2 > parrot-$(VERSION).tar.bz2.sha256
	mv MANIFEST.real MANIFEST
	rm parrot-$(VERSION)

win32-inno-installer : world installable
	$(PERL) tools/dev/mk_inno.pl
	$(INNO_SETUP) parrot.iss

###############################################################################
#
# exec:
#
###############################################################################

exec : src/parrot_config$(O) $(LIBPARROT)
	$(LINK) @ld_out@$(EXEC)$(EXE) $(EXEC)$(O) src/parrot_config$(O) @rpath_blib@ $(ALL_PARROT_LIBS) $(LINKFLAGS)

###### OS depend targets ##########

# for use by t/pmc/nci.t
## SUFFIX OVERRIDE - dynloaded files need cc_shared
src/nci_test$(O): $(PARROT_H_HEADERS) src/nci_test.c
	$(CC) $(CFLAGS) @optimize::src/nci_test.c@ @ccwarn::src/nci_test.c@ @cc_shared@ -I$(@D) @cc_o_out@$@ -c src/nci_test.c

$(LIBNCI_TEST_SO): src/nci_test$(O) $(LIBPARROT)
	$(LD) $(LD_LOAD_FLAGS) @ncilib_link_extra@ $(LDFLAGS) \
    @ld_out@$@ src/nci_test$(O) $(C_LIBS)

# for use by runtime/parrot/library/OpenGL.pir
src/glut_callbacks$(O): $(PARROT_H_HEADERS) \
    $(INC_DIR)/extend.h $(INC_DIR)/extend_vtable.h src/glut_callbacks.c

src/glut_nci_thunks.c: $(NCI_THUNK_GEN)
	$(NCI_THUNK_GEN) \
		--loader-name=Parrot_glut_nci_loader \
		--loader-storage-class=PARROT_DYNEXT_EXPORT \
		--output=src/glut_nci_thunks.c \
		<src/glut_nci_thunks.nci

src/glut_nci_thunks$(O) : $(PARROT_H_HEADERS) \
    src/glut_nci_thunks.c \
    include/pmc/pmc_nci.h

$(LIBGLUTCB_SO): $(LIBPARROT) src/glut_callbacks$(O) src/glut_nci_thunks$(O)
	$(LD) $(LD_LOAD_FLAGS) $(LDFLAGS) \
    @ld_out@$@ src/glut_callbacks$(O) src/glut_nci_thunks$(O) \
    $(ALL_PARROT_LIBS) @opengl_lib@

src/extra_nci_thunks.c : src/nci/extra_thunks.nci $(NCI_THUNK_GEN)
	$(NCI_THUNK_GEN) --dynext --no-warn-dups \
		--output=src/extra_nci_thunks.c <src/nci/extra_thunks.nci
#
# remove the following two lines commited in r48180 which cause this to be re-generated
# every time the all target is invoked - see TT #1719
#
#	$(NCI_THUNK_GEN) --core --loader-name=Parrot_nci_load_extra_thunks --no-warn-dups \
#		--output=src/nci/extra_thunks.c <src/nci/extra_thunks.nci

## SUFFIX OVERRIDE
src/extra_nci_thunks$(O) : $(PARROT_H_HEADERS) src/extra_nci_thunks.c \
    include/pmc/pmc_nci.h
	$(CC) $(CFLAGS) @optimize::src/extra_nci_thunks.c@ @ccwarn::src/extra_nci_thunks.c@ @cc_shared@ -I$(@D) @cc_o_out@$@ -c src/extra_nci_thunks.c

$(EXTRANCITHUNKS_SO) : $(LIBPARROT) src/extra_nci_thunks$(O)
	$(LD) $(LD_LOAD_FLAGS) $(LDFLAGS) \
    @ld_out@$@ src/extra_nci_thunks$(O) \
    $(ALL_PARROT_LIBS)

# emacs etags
# this needs exuberant-ctags

tags-emacs: tags.emacs.dummy
	$(RM_F) TAGS
	@ctags@ -e \
	--links=no --totals \
	-R --exclude=blib --exclude=.svn  \
	--languages=c,perl --langmap=c:+.h,c:+.pmc,c:+.ops \
	-I NOTNULL,NULLOK,ARGIN,ARGMOD,ARGOUT,ARGINOUT,ARGIN_NULLOK,ARGOUT_NULLOK,ARGMOD_NULLOK,ARGFREE,ARGFREE_NOTNULL \
	.

# this works with an old etags (XEmacs 21.5*)
tags-xemacs: tags.emacs.dummy
	$(RM_F) TAGS
	find . \
	-name \*.c -o -name \*.h -o -name \*.pmc -o -name \*.ops | etags -l c - -o TAGS

tags.emacs.dummy:

# vim ctags
# this needs exuberant-ctags

tags-vi: tags.vi.dummy
	$(RM_F) tags
	@ctags@ \
	--links=no --totals \
	-R --exclude=blib --exclude=.svn  \
	--languages=c,perl --langmap=c:+.h,c:+.pmc,c:+.ops \
	-I NOTNULL,NULLOK,ARGIN,ARGMOD,ARGOUT,ARGINOUT,ARGIN_NULLOK,ARGOUT_NULLOK,ARGMOD_NULLOK,ARGFREE,ARGFREE_NOTNULL \
	.
	$(PERL) $(BUILD_TOOLS_DIR)/addopstags.pl $(OPS_FILES)

tags.vi.dummy:

tags: tags.dummy
	@echo 'There is no "tags" target. You want tags-vi or tags-emacs.'

tags.dummy:

CRITIC_FILES = 'lib/Parrot'

perlcritic:
	perlcritic --profile tools/util/perlcritic.conf $(CRITIC_FILES)

# Andy's extra-cranky Perl::Critic checking for cage cleaners
cagecritic:
	@perl -MPerl::Critic::Bangs -e'$$min=q{1.04};die qq{You need Bangs $$min} unless $$Perl::Critic::Bangs::VERSION ge $$min'
	perlcritic -1 --profile tools/util/perlcritic-cage.conf $(CRITIC_FILES)

# This target will eventually create all the headers automatically.  If you
# are having problems with linkage in Win32 (or elsewhere), because something
# is not PARROT_EXPORT but should be, then put PARROT_EXPORT in the C file and
# run "make headerizer".  The .h file will get updated.

HEADERIZER_O_FILES = \
    $(O_FILES) \
    src/main$(O) \
    src/packdump$(O) \
    src/pbc_merge$(O) \
    $(PIRC_O_FILES)

headerizer : src/core_pmcs.c
	$(HEADERIZER) $(HEADERIZER_O_FILES) compilers/imcc/imcc.y

apilist: src/core_pmcs.c
	$(HEADERIZER) --macro=PARROT_API $(HEADERIZER_O_FILES)

exportlist: src/core_pmcs.c
	$(HEADERIZER) --macro=PARROT_EXPORT $(HEADERIZER_O_FILES)

malloclist: src/core_pmcs.c
	$(HEADERIZER) --macro=PARROT_MALLOC $(HEADERIZER_O_FILES)

include src/dynpmc/Rules.mak
include src/dynoplibs/Rules.mak
include runtime/parrot/library/Rules.mak
include compilers/imcc/Rules.mak
include compilers/pirc/Rules.mak
include compilers/pge/Rules.mak
include compilers/pct/Rules.mak
include compilers/opsc/Rules.mak
include compilers/tge/Rules.mak
include compilers/data_json/Rules.mak
include ext/nqp-rx/Rules.mak

# Local variables:
#   mode: makefile
# End:
# vim: ft=make:
