# HG changeset patch # User Claus Gittinger # Date 1255093788 -7200 # Node ID 876679f78999d6d09de3889b9e56448dabe6dd51 # Parent e1eeda9d1639a2695621dea3954fbfe5f48bb038 initial checkin diff -r e1eeda9d1639 -r 876679f78999 ProjectBuilder.st --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/ProjectBuilder.st Fri Oct 09 15:09:48 2009 +0200 @@ -0,0 +1,288 @@ +"{ Package: 'stx:libtool2' }" + +Object subclass:#ProjectBuilder + instanceVariableNames:'package projectDefinitionClass sourceCodeManager buildDirectory + myWorkingDirectory mySTXTopDirectory' + classVariableNames:'PreviousBuildDirectory' + poolDictionaries:'' + category:'System-Support-Projects' +! + + +!ProjectBuilder class methodsFor:'examples'! + +example1 + Smalltalk loadPackage:'stx:projects/helloWorldApp' asAutoloaded:true. + + self new + package:'stx:projects/helloWorldApp'; + build +! ! + +!ProjectBuilder methodsFor:'accessing'! + +package:aPackageIDOrSymbol + package := aPackageIDOrSymbol asPackageId. +! + +projectDefinitionClass:something + projectDefinitionClass := something. +! ! + +!ProjectBuilder methodsFor:'building'! + +build + "/ intermediate - this will move into a commonly used utility class + "/ (where all the project code support will be collected). + + |module directory| + + projectDefinitionClass := ProjectDefinition definitionClassForPackage:package. + projectDefinitionClass isNil ifTrue:[ + self error:('Missing ProjectDefinition class for "',package asString,'"') + ]. + + "/ ensure that everything is loaded... + projectDefinitionClass loadAsAutoloaded:false. + projectDefinitionClass loadExtensions. + projectDefinitionClass loadAllClassesAsAutoloaded:false. + +self halt. + module := package module. + directory := package directory. + + buildDirectory := PreviousBuildDirectory ifNil:[ UserPreferences current buildDirectory ]. + buildDirectory isNil ifTrue:[ + buildDirectory := Filename tempDirectory construct:'stx_build'. + ]. + buildDirectory := buildDirectory asFilename. + + "/ self validateBuildDirectoryIsPresent. + + PreviousBuildDirectory := buildDirectory. + + "/ UserPreferences current localBuild:true + UserPreferences current localBuild ifFalse:[ + SourceCodeManager notNil ifTrue:[ + sourceCodeManager := SourceCodeManagerUtilities sourceCodeManagerFor:projectDefinitionClass. + ] + ]. + sourceCodeManager := nil. + + mySTXTopDirectory := + Smalltalk packagePath + detect:[:aPath | + (aPath asFilename / 'stx' / 'include') exists + and: [ (aPath asFilename / 'stx' / 'rules') exists ]] + ifNone:nil. + mySTXTopDirectory isNil ifTrue:[ + self error:('Cannot figure out my top directory (where include and rules are)') + ]. + + self setupBuildDirectory. + self generateSourceFiles. + + OperatingSystem + executeCommand:(ParserFlags makeCommand) + inputFrom:nil + outputTo:Transcript + errorTo:Transcript + inDirectory:((buildDirectory construct:module) construct:directory) + onError:[:status| self error:'make failed']. + + "Created: / 09-08-2006 / 18:37:19 / fm" + "Modified: / 09-08-2006 / 19:55:50 / fm" + "Modified: / 22-09-2006 / 17:37:11 / cg" +! + +copyDirectory:relativepath + "/ need rules in stx + ((Smalltalk projectDirectoryForPackage:'stx') asFilename construct:relativepath) + recursiveCopyTo:(buildDirectory construct:'stx'). +! + +copyDirectoryForBuild:subdir + |targetDir| + + targetDir := buildDirectory / 'stx' / subdir. + targetDir exists ifFalse:[ + targetDir makeDirectory. + (mySTXTopDirectory / subdir) directoryContentsAsFilenamesDo:[:eachFile | + eachFile isDirectory ifFalse:[ + eachFile copyTo:(targetDir construct:eachFile baseName) + ] + ]. + ]. +! + +generateSourceFiles + sourceCodeManager notNil ifTrue:[ + "/ check out / generate files there + self generateSourceFilesByCheckingOutUsing:sourceCodeManager + ] ifFalse:[ + "/ local build + "/ fileout the project + self generateSourceFilesByFilingOut + ] +! + +generateSourceFilesByCheckingOutUsing:aSourceCodeManager + "/ will no longer be needed/supported + + |repository stxRepository module directory| + +self halt. + "/ check out / generate files there + repository := (aSourceCodeManager repositoryNameForModule:module) ifNil:[aSourceCodeManager repositoryName]. + stxRepository := aSourceCodeManager repositoryName. + + (buildDirectory construct:'stx') exists ifFalse:[ + (module ~= 'stx') ifTrue:[ + OperatingSystem + executeCommand:('cvs -d ',stxRepository,' co stx') + inputFrom:nil + outputTo:Transcript + errorTo:Transcript + inDirectory:buildDirectory + onError:[:status| self error:'cvs update stx failed']. + ]. + ]. + + ((buildDirectory construct:module) construct:'CVS') exists ifFalse:[ + OperatingSystem + executeCommand:('cvs -d ',repository,' co -l ',directory) + inputFrom:nil + outputTo:Transcript + errorTo:Transcript + inDirectory:buildDirectory + onError:[:status| self error:'cvs update failed']. + ]. + OperatingSystem + executeCommand:'cvs upd -d' + inputFrom:nil + outputTo:Transcript + errorTo:Transcript + inDirectory:(buildDirectory construct:module) + onError:[:status| self error:'cvs update failed']. +self halt. +! + +generateSourceFilesByFilingOut + |targetDir prerequisitePackages| + + "/ local build + "/ fileout the project + + (package module ~= 'stx') ifTrue:[ + (buildDirectory / package module) makeDirectory. + ]. + + "/ file out the package(s) + + ((Array with:package) , (projectDefinitionClass allPreRequisites)) + do:[:eachPackageToFileout | + |packageModule packageDirectory packageTargetDir| + + packageModule := eachPackageToFileout asPackageId module. + packageDirectory := eachPackageToFileout asPackageId directory. + packageTargetDir := (buildDirectory / packageModule / packageDirectory) recursiveMakeDirectory. + + (Smalltalk allClassesInPackage:eachPackageToFileout) do:[:cls | + cls isPrivate ifFalse:[ + cls isLoaded ifFalse:[ + self halt. + cls autoload. + ]. + cls fileOutIn:packageTargetDir + ] + ]. + ]. + +"/ "/ copy h-files preRequisite packages +"/ prerequisitePackages := projectDefinitionClass preRequisitesForBuilding. +"/ prerequisitePackages do:[:eachPackage | +"/ |relativeDir sourceDir| +"/ +"/ relativeDir := eachPackage asPackageId pathRelativeToTopDirectory. +"/ sourceDir := Smalltalk packageDirectoryForPackageId:eachPackage. +"/ targetDir := buildDirectory construct:relativeDir. +"/ targetDir recursiveMakeDirectory. +"/ sourceDir directoryContentsAsFilenamesDo:[:eachSourceFilename | +"/ ((eachSourceFilename suffix asLowercase = 'h') +"/ or:[ eachSourceFilename suffix asLowercase = 'sth' ]) ifTrue:[ +"/ eachSourceFilename copyTo:targetDir. +"/ ]. +"/ ]. +"/ ]. + +"/ stx_libbasic2 preRequisitesForBuilding#(#'stx:libbasic') +"/ "/ generate support files there +"/ targetDir := ((buildDirectory construct:module) construct:directory) recursiveMakeDirectory. +"/ #('bmake.bat' 'Make.spec' 'Make.proto' 'libInit.cc' 'abbrev.stc' +"/ 'bc.mak' +"/ ) do:[:f | +"/ |contents| +"/ +"/ contents := projectDefinitionClass generateFile:f. +"/ (targetDir construct:f) contents:contents. +"/ ]. +! + +setupBuildDirectory + buildDirectory exists ifFalse:[ + buildDirectory recursiveMakeDirectory. + ]. + (buildDirectory / 'stx') exists ifFalse:[ + (buildDirectory / 'stx') makeDirectory. + ]. + + self copyDirectoryForBuild:'include'. + self copyDirectoryForBuild:'rules'. +! + +validateBuildDirectoryIsPresent + + ^ self. + +"/ [ +"/ |default directoryIsOKForMe stc | +"/ +"/ default := (buildDirectory ? +"/ PreviousBuildDirectory) +"/ ifNil:[ UserPreferences current buildDirectory]. +"/ +"/ buildDirectory := Dialog requestDirectoryName:'Temporary Work-ROOT for build:' +"/ default:default. +"/ +"/ buildDirectory isEmptyOrNil ifTrue:[^ self]. +"/ buildDirectory := buildDirectory asFilename. +"/ directoryIsOKForMe := true. +"/ +"/ buildDirectory exists ifFalse:[ +"/ Dialog warn:(self classResources string:'Work directory %1 does not exist.' with:buildDirectory). +"/ directoryIsOKForMe := false. +"/ ] ifTrue:[ +"/ (buildDirectory construct:'stx') exists ifFalse:[ +"/ Dialog warn:(self classResources stringWithCRs:'Work directory must contain an stx subDirectory,\which contains (at least) the stc and include subdirectories.'). +"/ directoryIsOKForMe := false. +"/ ] ifTrue:[ +"/ stc := (OperatingSystem isMSDOSlike) ifTrue:['stc.exe'] ifFalse:['stc']. +"/ (((buildDirectory construct:'stx')construct:'stc')construct:stc) exists ifFalse:[ +"/ Dialog warn:(self classResources stringWithCRs:'Work directory must contain an stc compiler in the stx/stc subDirectory.'). +"/ directoryIsOKForMe := false. +"/ ]. +"/ ((buildDirectory construct:'stx')construct:'include') exists ifFalse:[ +"/ Dialog warn:(self classResources stringWithCRs:'Work directory must have had a make run before (for include files to exists).'). +"/ directoryIsOKForMe := false. +"/ ]. +"/ ] +"/ ]. +"/ directoryIsOKForMe +"/ ] whileFalse +! ! + +!ProjectBuilder class methodsFor:'documentation'! + +version_CVS + ^ '$Header$' +! !