Changes to make fptools insfrastructure usable for standalone
libraries
Alastair Reid
alastair at reid-consulting-uk.ltd.uk
Wed May 21 07:20:40 EDT 2003
> I think the right way to fix this is to introduce a toggle that selects
> between the current behaviour and a mode which builds packages
> specifically for use with an pre-existing GHC installation. Let's call
> this "standalone package mode".
I'm attaching my current version of package.mk. Rather than add a new
variable for when we're in standalone mode, I used this test to determine
whether we were in standalone mode or not:
ifneq "$(GHC_DRIVER_DIR)" ""
This works because GHC_DRIVER_DIR is one of the variables currently used in
package.mk - not having it set is what originally caused me to fall over.
Almost all the differences between the two modes are encapsulated in a bunch
of definitions at the top which define variables used in package.mk:
ifneq "$(GHC_DRIVER_DIR)" ""
PKG_INSTALL_DIR = $(GHC_DRIVER_DIR)
PKG_INCLUDE_DIR = $(GHC_INCLUDE_DIR)
STAMP_PKG_CONF = $(GHC_DRIVER_DIR)/stamp-pkg-conf-$(PACKAGE)
PKG_PROG = $(GHC_PKG_INPLACE)
PKG_GHC = $(GHC_INPLACE)
else
PKG_INSTALL_DIR = $(shell $(GHC) "--print-libdir")
PKG_INCLUDE_DIR = $(PKG_INSTALL_DIR)/include
STAMP_PKG_CONF = $(TOP)/stamp-pkg-conf-$(PACKAGE)
PKG_PROG = $(GHC_PKG)
PKG_GHC = $(GHC)
endif
I used the PKG_ for all new variables and am tempted to rename STAMP_PKG_CONF
to fit this convention (PKG_CONF_STAMP?)
Three changes I couldn't isolate in this bit of code are:
1) mk/target.mk needs this change.
Possible fix: move the definition of PKGCONF_DEP to package.mk.
I haven't done so because I'm not sure what PKGCONF_DEP is for
- I couldn't see anything that used it in the existing system.
*** target.mk 27 Apr 2003 10:30:13 -0000 1.173
--- target.mk 21 May 2003 10:55:15 -0000
***************
*** 78,89 ****
MKDEPENDHS_OBJ_SUFFICES=o
ifneq "$(STAMP_PKG_CONF)" ""
PKGCONF_DEP = $(STAMP_PKG_CONF)
else
PKGCONF_DEP =
endif
! depend :: $(MKDEPENDHS_SRCS) $(MKDEPENDC_SRCS) $(STAMP_PKG_CONF)
@$(RM) .depend
@touch .depend
ifneq "$(DOC_SRCS)" ""
--- 78,93 ----
MKDEPENDHS_OBJ_SUFFICES=o
ifneq "$(STAMP_PKG_CONF)" ""
+ ifneq "$(GHC_DRIVER_DIR)" ""
PKGCONF_DEP = $(STAMP_PKG_CONF)
else
PKGCONF_DEP =
endif
+ else
+ PKGCONF_DEP =
+ endif
! depend :: $(MKDEPENDHS_SRCS) $(MKDEPENDC_SRCS) $(PKGCONF_DEP)
@$(RM) .depend
@touch .depend
ifneq "$(DOC_SRCS)" ""
2) The code that invoked ghc-pkg < package.conf.{inplace,installed}.
In standalone mode, we install just package.conf.installed but
in inplace mode we install package.conf.inplace too.
I don't fully grok:
a) why you install two copies
b) why you install both at boot time instead of installing one
at install time
c) why they have the same stamp file
So I'm struggling for what changes might be reasonable here.
What I have works but feels inelegant.
> You *could* put libraries in the GHC install dir, but it might be
> cleaner to put them in their own directories: /usr/lib/<yourlibrary>.
> This *should* happen automatically if you set up the mk stuff as
> described above.
At the moment, I'm continuing to put them in the ghc install directory
by putting this at the head of every Makefile (yeuch)
libdir = $(shell $(GHC) "--print-libdir")
This has the strength of including the ghc version number in the directory
name - though I guess I could use:
/usr/lib/yourlibrary/`ghc --version`
(well, almost - need to cleanup the string ghc --version returns).
[Hmmm, maybe I should leave this up to the person running configure?
To make this work, I just have to take care that I install in a subdirectory
of libdir not in libdir itself since pissing all over /usr/lib probably won't
win many friends.]
My example library Makefile now contains this header. The FPTOOLS_TOP part is
the most interesting (and, yes, it _does_ have to come after boilerplate to
avoid being overridden).
TOP = .
include $(TOP)/mk/boilerplate.mk
FPTOOLS_TOP := ../..
libdir = $(shell $(GHC) "--print-libdir")
My Makefile also takes care to define:
HIERARCHICAL_LIB = YES
(can we make hierarchical the default instead?)
--
Alastair Reid
-------------- next part --------------
# -----------------------------------------------------------------------------
# $Id: package.mk,v 1.25 2003/05/17 00:11:30 ross Exp $
ifneq "$(PACKAGE)" ""
ifneq "$(GHC_DRIVER_DIR)" ""
PKG_INSTALL_DIR = $(GHC_DRIVER_DIR)
PKG_INCLUDE_DIR = $(GHC_INCLUDE_DIR)
STAMP_PKG_CONF = $(GHC_DRIVER_DIR)/stamp-pkg-conf-$(PACKAGE)
PKG_PROG = $(GHC_PKG_INPLACE)
PKG_GHC = $(GHC_INPLACE)
else
PKG_INSTALL_DIR = $(shell $(GHC) "--print-libdir")
PKG_INCLUDE_DIR = $(PKG_INSTALL_DIR)/include
STAMP_PKG_CONF = $(TOP)/stamp-pkg-conf-$(PACKAGE)
PKG_PROG = $(GHC_PKG)
PKG_GHC = $(GHC)
endif
# -----------------------------------------------------------------------------
# Build the package configuration file and tell the compiler about it.
ifeq "$(way)" ""
package.conf.inplace : package.conf.in
$(CPP) $(RAWCPP_FLAGS) -I$(PKG_INCLUDE_DIR) -x c $(PACKAGE_CPP_OPTS) $< \
| sed 's/^#.*$$//g' >$@
package.conf.installed : package.conf.in
$(CPP) $(RAWCPP_FLAGS) -I$(PKG_INCLUDE_DIR) -DINSTALLING -x c $(PACKAGE_CPP_OPTS) $< \
| sed 's/^#.*$$//g' >$@
# we could be more accurate here and add a dependency on
# ghc/driver/package.conf, but that doesn't work too well because of
# make's limited accuracy with modification times: when doing 'make
# boot' in multiple packages, make won't detect that the package
# configuration needs updating if it was updated already in the last
# second.
#
# The stamp file goes in $(GHC_DRIVER_DIR), so that if someone happens
# to 'make clean' in ghc without cleaning in libraries too, the packages
# will be correctly re-installed.
#
CLEAN_FILES += $(STAMP_PKG_CONF)
ifneq "$(GHC_DRIVER_DIR)" ""
ifneq "$(BootingFromHc)" "YES"
boot all :: $(STAMP_PKG_CONF)
endif
# ToDo: should be installing in two different places
$(STAMP_PKG_CONF) : package.conf.inplace package.conf.installed
$(PKG_PROG) -f $(PKG_INSTALL_DIR)/package.conf --update-package < package.conf.inplace
$(PKG_PROG) --update-package < package.conf.installed
@touch $(STAMP_PKG_CONF)
else
install :: $(STAMP_PKG_CONF)
$(STAMP_PKG_CONF) : package.conf.installed
$(PKG_PROG) --update-package < package.conf.installed
@touch $(STAMP_PKG_CONF)
endif
CLEAN_FILES += package.conf.installed package.conf.inplace
endif # $(way) == ""
# -----------------------------------------------------------------------------
# Building the static library libHS<pkg>.a
HC = $(PKG_GHC)
SRC_HSC2HS_OPTS += -I.
ifeq "$(NON_HS_PACKAGE)" ""
SRC_HC_OPTS += -package-name $(PACKAGE)
SRC_HC_OPTS += $(GhcLibHcOpts)
SRC_HC_OPTS += $(patsubst %, -package %, $(PACKAGE_DEPS))
endif
LIBRARY = libHS$(PACKAGE)$(_way).a
WAYS = $(GhcLibWays)
all :: $(LIBRARY)
# POSSIBLE alternative version using --make:
#
# lib : $(HS_SRCS)
# $(GHC_INPLACE) $(HC_OPTS) --make $(HS_SRCS)
#
# $(LIBNAME) : lib
# $(RM) $@
# $(AR) $(AR_OPTS) $@ $(HS_OBJS)
# $(RANLIB) $@
#
# %.o : %.hs
# $(GHC_INPLACE) $(HC_OPTS) --make $<
# %.o : %.lhs
# $(GHC_INPLACE) $(HC_OPTS) --make $<
# -----------------------------------------------------------------------------
# Installation; need to install .hi files as well as libraries
ifeq "$(DLLized)" "YES"
INSTALL_PROGS += $(DLL_NAME)
INSTALL_LIBS += $(patsubst %.a,%_imp.a, $(LIBRARY))
endif
# The interface files are put inside the $(libdir), since they
# might (potentially) be platform specific..
ifeq "$(HIERARCHICAL_LIB)" "YES"
ifacedir = $(libdir)/imports/$(PACKAGE)
else
ifacedir = $(libdir)/hslibs-imports/$(PACKAGE)
endif
# If the lib consists of a hierachy of modules, we must retain the directory
# structure when we install the interfaces.
ifeq "$(HIERARCHICAL_LIB)" "YES"
INSTALL_IFACES_WITH_DIRS += $(HS_IFACES)
ifneq "$(ALL_DIRS)" ""
install ::
@for i in $(ALL_DIRS); do \
$(INSTALL_DIR) $(ifacedir)/$$i; \
done
endif
else
INSTALL_IFACES += $(HS_IFACES)
endif
# -----------------------------------------------------------------------------
# Dependencies
MKDEPENDHS = $(PKG_GHC)
SRC_MKDEPENDC_OPTS += $(addprefix -I,$(ALL_DIRS)) -I$(PKG_INCLUDE_DIR)
endif # $(PACKAGE) /= ""
# install library (could be implicitly specified or explicitly, like libHS*_cbits.a)
INSTALL_LIBS += $(LIBRARY)
#--------------------------------------------------------------
# Building dynamically-linkable libraries for GHCi
#
# Build $(GHCI_LIBRARY) whenever we build $(LIBRARY)
#
# Why? GHCi can only link .o files (at the moment), not .a files
# so we have to build libFoo.o as well as libFoo.a
#
# Furthermore, GHCi currently never loads
# profiling libraries (or other non-std ways)
ifneq "$(LIBRARY)" ""
ifeq "$(way)" ""
ifeq "$(GhcWithInterpreter)" "YES"
GHCI_LIBRARY = $(patsubst lib%.a,%.o,$(LIBRARY))
INSTALL_LIBS += $(GHCI_LIBRARY)
CLEAN_FILES += $(GHCI_LIBRARY)
all :: $(GHCI_LIBRARY)
ifneq "$(DONT_WANT_STD_GHCI_LIB_RULE)" "YES"
# If you don't want to build GHCI_LIBRARY the 'standard' way,
# set DONT_WANT_STD_GHCI_LIB_RULE to YES. The Prelude and
# hslibs/Win32 uses this 'feature', which will go away soon
# when we can use a "fixed" ld.
#
$(GHCI_LIBRARY) : $(LIBOBJS)
$(LD) -r $(LD_X) -o $@ $(STUBOBJS) $(LIBOBJS)
endif # DONT_WANT_STD_GHCI_LIB_RULE
endif # GhcWithInterpreter
endif # way
# -----------------------------------------------------------------------------
# Doc building with Haddock
ifneq "$(NO_HADDOCK_DOCS)" "YES"
HS_PPS = $(addsuffix .raw-hs, $(basename $(filter-out $(EXCLUDED_HADDOCK_SRCS), $(HS_SRCS))))
HTML_DIR = html
HTML_DOC = $(HTML_DIR)/index.html
ifneq "$(HS_PPS)" ""
CLEAN_FILES += $(HS_PPS) $(addsuffix .tmp, $(HS_SRCS))
ifeq "$(HADDOCK)" ""
html ::
@echo Haddock must be installed in order to build HTML library documentation.
@echo Please install Haddock and re-configure.
@exit 1
endif
html :: $(HTML_DOC)
extraclean ::
$(RM) -rf $(HTML_DIR)
$(HTML_DOC) : $(HS_PPS)
@$(INSTALL_DIR) $(HTML_DIR)
$(HADDOCK) $(HADDOCK_OPTS) -h -o $(HTML_DIR) $(HS_PPS) \
--dump-interface=$(PACKAGE).haddock \
$(foreach pkg, $(PACKAGE_DEPS), \
--read-interface=../$(pkg),../$(pkg)/$(pkg).haddock)
%.raw-hs : %.lhs
$(GHC_INPLACE) $(HC_OPTS) -D__HADDOCK__ -E -cpp $< -o $<.tmp && sed -e 's/^#.*//' <$<.tmp >$@
%.raw-hs : %.hs
$(GHC_INPLACE) $(HC_OPTS) -D__HADDOCK__ -E -cpp $< -o $<.tmp && sed -e 's/^#.*//' <$<.tmp >$@
install-docs :: $(HTML_DOC)
@$(INSTALL_DIR) $(datadir)/html/$(PACKAGE)
@for i in $(HTML_DIR)/*; do \
echo $(INSTALL_DATA) $(INSTALL_OPTS) $$i $(datadir)/html/$(PACKAGE); \
$(INSTALL_DATA) $(INSTALL_OPTS) $$i $(datadir)/html/$(PACKAGE); \
done
$(INSTALL_DATA) $(INSTALL_OPTS) $(PACKAGE).haddock $(datadir)/html/$(PACKAGE)
endif # HS_PPS
endif # NO_HADDOCK_DOCS
# -----------------------------------------------------------------------------
endif # $(LIBRARY) /= ""
More information about the Glasgow-haskell-bugs
mailing list