1 # Copyright (c) 2023, 2024, Oracle and/or its affiliates. All rights reserved.
  2 # DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  3 #
  4 # This code is free software; you can redistribute it and/or modify it
  5 # under the terms of the GNU General Public License version 2 only, as
  6 # published by the Free Software Foundation.
  7 #
  8 # This code is distributed in the hope that it will be useful, but WITHOUT
  9 # ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 10 # FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 11 # version 2 for more details (a copy is included in the LICENSE file that
 12 # accompanied this code).
 13 #
 14 # You should have received a copy of the GNU General Public License version
 15 # 2 along with this work; if not, write to the Free Software Foundation,
 16 # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 17 #
 18 # Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 19 # or visit www.oracle.com if you need additional information or have any
 20 # questions.
 21 
 22 #===============================================================================
 23 # Leyden-premain + spring-petclinic demo (https://github.com/spring-projects/spring-petclinic)
 24 #
 25 # Build spring-petclinic:
 26 #    make app
 27 #
 28 # Build all leyden optimization artifacts (this is using the older "4 step training run" which will be simplified):
 29 #    make aot
 30 #
 31 # Run with Leyden optimizations
 32 #    make run
 33 #
 34 # Run without Leyden optimizations
 35 #    make run0
 36 
 37 # Set the following to point to JDK 17 and your Leyden JDK build.
 38 #
 39 #  *** NOTE: JDK 17 (or 21??) is needed to build spring-petclinic-3.2.0-SNAPSHOT.jar
 40 JDK17_HOME   = /jdk3/official/jdk17
 41 PREMAIN_HOME = /jdk3/bld/le4/images/jdk
 42 #===============================================================================
 43 
 44 # Usually there's no need to change the following
 45 JAR_CMD          = ${JDK17_HOME}/bin/jar
 46 JDK17_JAVA       = ${JDK17_HOME}/bin/java
 47 PREMAIN_JAVA     = ${PREMAIN_HOME}/bin/java
 48 PC_REPO          = petclinic-snapshot
 49 PC_JAVA_SOURCES = ${PC_REPO}/src/main/java/org/springframework/samples/petclinic/PetClinicApplication.java
 50 PC_APP_JAR       = ${PC_REPO}/target/spring-petclinic-3.2.0-SNAPSHOT.jar
 51 PC_APP_UNPACKED  = ${PC_REPO}/target/unpacked
 52 
 53 # This is for uploading to artifactory, to be tested with
 54 # ../../runtime/cds/appcds/leyden/SpringPetClinic.java
 55 PC_APP_UNPACKED_ZIP = ${PC_REPO}/target/spring-petclinic-3.2.0.zip
 56 
 57 PC_MAIN_CLASS    = org.springframework.samples.petclinic.PetClinicApplication
 58 PC_CLASSLIST     = spring-petclinic.classlist
 59 PC_STATIC_JSA    = spring-petclinic.static.jsa
 60 PC_DYNAMIC_JSA   = spring-petclinic.dynamic.jsa
 61 PC_CACHED_CODE   = spring-petclinic.code.jsa
 62 
 63 # new workflow
 64 PC_CDS_PREIMAGE  = spring-petclinic.cds.preimage
 65 PC_CDS           = spring-petclinic.cds
 66 
 67 # TODO: should we add -Dspring.context.exit=onRefresh to command line??
 68 # This will make the JVM quit after printing this line:
 69 #
 70 #    4:21.639 ... o.s.b.a.e.web.EndpointLinksResolver      : Exposing 13 endpoint(s) beneath base path '/actuator'
 71 #
 72 # Whereas -DautoQuit=true will make it exit after printing the following (a little bit of application code is executed)
 73 #
 74 #    4:21.665 ... o.s.b.w.embedded.tomcat.TomcatWebServer  : Tomcat started on port 8080 (http) with context path ''
 75 #    4:21.666 ... o.s.s.petclinic.PetClinicApplication     : Started PetClinicApplication in 1.358 seconds (process running for 1.584)
 76 #    #### Booted and returned in 1453ms
 77 #    4:21.692 ... j.LocalContainerEntityManagerFactoryBean : Closing JPA EntityManagerFactory for persistence unit 'default'
 78 #    4:21.693 ... com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Shutdown initiated...
 79 #    4:21.694 ... com.zaxxer.hikari.HikariDataSource       : HikariPool-1 - Shutdown completed.
 80 HEAP_SIZE        = -Xmx2g
 81 UNPACKED_CMDLINE = $(HEAP_SIZE) -cp @${PC_APP_UNPACKED}/classpath -DautoQuit=true -Dspring.aot.enabled=true -Dspring.output.ansi.enabled=NEVER ${PC_MAIN_CLASS}
 82 
 83 all: check git app aot
 84 
 85 check:
 86 	@if ${JDK17_JAVA} --version | grep -q '17.*LTS'; then \
 87 	    true; \
 88 	else \
 89 	    echo JDK17_HOME should point to JDK 17; \
 90 	    exit 1; \
 91 	fi
 92 	@if ${PREMAIN_JAVA} -XX:+PrintFlagsFinal --version | grep -q ArchiveInvokeDynamic; then \
 93 	    true; \
 94 	else \
 95 	    echo PREMAIN_HOME should point to your build of https://github.com/openjdk/leyden/tree/premain; \
 96 	    exit 1; \
 97 	fi
 98 
 99 # A bunch of quick targets so you can type "make list" to create the classlist, etc
100 git: ${PC_JAVA_SOURCES}
101 app: ${PC_APP_JAR}
102 unpack: ${PC_APP_UNPACKED}
103 
104 # The "4 step training run" workflow -- this will soon be replaced with the new workflow in ../javac_new_workflow/
105 list: ${PC_CLASSLIST}
106 static: ${PC_STATIC_JSA}
107 dynamic: ${PC_DYNAMIC_JSA}
108 aot: ${PC_CACHED_CODE}
109 
110 # Check out this specific version of spring-petclinic that we have been testing with.
111 # https://github.com/spring-projects/spring-petclinic/commit/80fd11067c4662486e4c635deceba927375b621c
112 #    Author: Dave Syer <dsyer@vmware.com>
113 #    Date:   Wed Jan 10 05:01:00 2024
114 #        Upgrade to Boot 3.2.1
115 ${PC_JAVA_SOURCES}:
116 	rm -rf ${PC_REPO}
117 	git clone https://github.com/spring-projects/spring-petclinic ${PC_REPO}
118 	cd ${PC_REPO}; git reset --hard 80fd11067c4662486e4c635deceba927375b621c
119 	cd ${PC_REPO}; git apply ../premain-patch.diff
120 
121 # Need to touch ${PC_APP_JAR} as mvn wants to set it the release date of 3.2.0-SNAPSHOT
122 ${PC_APP_JAR}: ${PC_JAVA_SOURCES}
123 	cd ${PC_REPO}; JAVA_HOME=${JDK17_HOME} mvn -Dmaven.test.skip=true package
124 	if test -f ${PC_APP_JAR}; then \
125 	    touch ${PC_APP_JAR}; \
126 	fi
127 
128 ${PC_APP_UNPACKED}: ${PC_APP_JAR}
129 	rm -rf ${PC_APP_UNPACKED}
130 	mkdir -p ${PC_APP_UNPACKED}
131 	cd ${PC_APP_UNPACKED} && \
132 	    ${JAR_CMD} xf ../spring-petclinic-3.2.0-SNAPSHOT.jar && \
133 	    ${JAR_CMD} cf classes.jar META-INF org && \
134             cd BOOT-INF/classes/ && \
135 	    ${JAR_CMD} cf classes.jar *
136 	echo ${PC_APP_UNPACKED}/classes.jar $$(find ${PC_APP_UNPACKED}/BOOT-INF -name \*.jar | sort) \
137 	    | sed -e 's/ /:/g' > ${PC_APP_UNPACKED}/classpath
138 	${JAR_CMD} cf0 ${PC_APP_UNPACKED_ZIP} ${PC_APP_UNPACKED}
139 	$(MAKE) run17
140 
141 #uncomment this to see the generated classes for dynamic proxies
142 #SAVE_GEN_FILES=-Djdk.proxy.ProxyGenerator.saveGeneratedFiles=true
143 
144 ${PC_CLASSLIST}: ${PC_APP_UNPACKED}
145 	${PREMAIN_JAVA} -Xshare:off -XX:DumpLoadedClassList=${PC_CLASSLIST} \
146 	    -Xlog:class+load=debug:file=spring-petclinic.classload.log ${SAVE_GEN_FILES} \
147 	    ${UNPACKED_CMDLINE}
148 	wc -lc ${PC_CLASSLIST}
149 
150 ${PC_STATIC_JSA}: ${PC_CLASSLIST}
151 	rm -f ${PC_STATIC_JSA}.log
152 	${PREMAIN_JAVA} -Xshare:dump -XX:SharedClassListFile=${PC_CLASSLIST} $(HEAP_SIZE) -cp @${PC_APP_UNPACKED}/classpath \
153 	    -XX:SharedArchiveFile=${PC_STATIC_JSA} -XX:+ArchiveInvokeDynamic -Xlog:cds=debug,cds+class=debug,cds+heap=warning,cds+resolve=debug:file=${PC_STATIC_JSA}.log
154 	ls -l ${PC_STATIC_JSA}
155 
156 ${PC_DYNAMIC_JSA}: ${PC_STATIC_JSA}
157 	rm -f ${PC_DYNAMIC_JSA} ${PC_DYNAMIC_JSA}.log
158 	${PREMAIN_JAVA} -XX:SharedArchiveFile=${PC_STATIC_JSA} -XX:ArchiveClassesAtExit=${PC_DYNAMIC_JSA} \
159 	    -Xlog:cds=debug,cds+class=debug,cds+resolve=debug:file=${PC_DYNAMIC_JSA}.log \
160 	    -XX:+RecordTraining ${UNPACKED_CMDLINE}
161 	ls -l ${PC_DYNAMIC_JSA}
162 
163 ${PC_CACHED_CODE}: ${PC_DYNAMIC_JSA}
164 	${PREMAIN_JAVA} -XX:SharedArchiveFile=${PC_DYNAMIC_JSA} -XX:+ReplayTraining -XX:+StoreCachedCode \
165 	     -XX:CachedCodeFile=${PC_CACHED_CODE} -XX:CachedCodeMaxSize=512M ${UNPACKED_CMDLINE}
166 	ls -l ${PC_CACHED_CODE}
167 
168 # run with premain optimizatipn
169 run: ${PC_CACHED_CODE}
170 	time ${PREMAIN_JAVA} -XX:SharedArchiveFile=${PC_DYNAMIC_JSA} -XX:+ReplayTraining -XX:+LoadCachedCode \
171 		-XX:CachedCodeFile=${PC_CACHED_CODE} -Xlog:init -Xlog:scc=error ${UNPACKED_CMDLINE}
172 
173 # run with just static CDS archive
174 runs: ${PC_STATIC_JSA}
175 	time ${PREMAIN_JAVA} -XX:SharedArchiveFile=${PC_STATIC_JSA} \
176 		-Xlog:init ${UNPACKED_CMDLINE}
177 
178 # run with just dynamic CDS archive
179 rund: ${PC_DYNAMIC_JSA}
180 	time ${PREMAIN_JAVA} -XX:SharedArchiveFile=${PC_DYNAMIC_JSA} \
181 		-Xlog:init ${UNPACKED_CMDLINE}
182 
183 # run WITHOUT premain optimizatipn
184 run0: ${PC_APP_UNPACKED}
185 	time ${PREMAIN_JAVA} -Xlog:init ${UNPACKED_CMDLINE}
186 
187 run17: ${PC_APP_UNPACKED}
188 	time ${JDK17_JAVA} ${UNPACKED_CMDLINE}
189 
190 #======================================== new workflow
191 pre: ${PC_CDS_PREIMAGE}
192 cds: ${PC_CDS}
193 
194 ${PC_CDS_PREIMAGE}: ${PC_APP_UNPACKED}
195 	rm -f ${PC_CDS_PREIMAGE} ${PC_CDS}
196 	${PREMAIN_JAVA} -XX:+ArchiveInvokeDynamic -XX:CachedCodeMaxSize=512M -XX:+UnlockDiagnosticVMOptions -XX:+CDSManualFinalImage -XX:CacheDataStore=${PC_CDS} \
197 	    -Xlog:cds=debug,cds+class=debug,cds+heap=warning,cds+resolve=debug:file=${PC_CDS_PREIMAGE}.log \
198 	    ${UNPACKED_CMDLINE}
199 	ls -l ${PC_CDS_PREIMAGE}
200 
201 ${PC_CDS}: ${PC_CDS_PREIMAGE}
202 	rm -f ${PC_CDS}
203 	${PREMAIN_JAVA} -XX:+ArchiveInvokeDynamic -XX:CachedCodeMaxSize=512M -XX:+UnlockDiagnosticVMOptions -XX:CDSPreimage=${PC_CDS_PREIMAGE} -XX:CacheDataStore=${PC_CDS} \
204 	    -Xlog:scc,cds=debug,cds+class=debug,cds+heap=warning,cds+resolve=debug:file=${PC_CDS}.log \
205 	    ${UNPACKED_CMDLINE}
206 	ls -l ${PC_CDS}
207 	ls -l ${PC_CDS}.code
208 
209 # run with NEW workflow
210 runn: ${PC_CDS}
211 	time ${PREMAIN_JAVA} -XX:CacheDataStore=${PC_CDS} -Xlog:init -Xlog:scc=error ${UNPACKED_CMDLINE}
212 
213 clean: clean0
214 	rm -rf *~ ${PC_REPO}
215 
216 # clean the the leyden artifacts
217 clean0:
218 	rm -fv spring-petclinic.*
219 
220 # clean the the leyden artifacts for the new workflow only
221 cleann:
222 	rm -fv spring-petclinic.cds.*