I2P Address: [http://git.idk.i2p]

Skip to content
Snippets Groups Projects
custom_rules.xml 26.1 KiB
Newer Older
  • Learn to ignore specific revisions
  • <?xml version="1.0" encoding="UTF-8"?>
    <project name="imported">
    
    
        <!-- override with i2psrc=path/to/source in local.properties -->
        <property name="i2psrc" value="../i2p.i2p" />
        <property name="i2pbase" location="${i2psrc}" />
        <available file="${i2psrc}" property="i2p.present" />
        <fail message="I2P source directory ${i2psrc} was not found. Install it there or set i2psrc=/path/to/source in local.properties" >
            <condition>
                <not>
                    <isset property="i2p.present" />
                </not>
            </condition>
        </fail>
        <echo message="Using I2P source at ${i2pbase}" />
    
    
    
        <!-- Utility scripts -->
    
        <!-- Split a string -->
        <scriptdef name="split" language="javascript">
                <attribute name="value"/>
                <attribute name="sep"/>
                <attribute name="prefix"/>
                <![CDATA[
                    values = attributes.get("value").split(attributes.get("sep"));
                    for(i = 0; i < values.length; i++) {
                            project.setNewProperty(attributes.get("prefix") + "." + i, values[i]);
                    }
                ]]>
        </scriptdef>
    
        <!-- Normalize the core version number -->
        <scriptdef name="setcore" language="javascript">
                <attribute name="value"/>
                <![CDATA[
                    value = attributes.get("value").split("\n")[0];
                    values = value.split('\\.');
                    dots = values.length - 1;
                    major = values[0];
                    minor = "0";
                    release = "0";
                    if(dots > 0) {
                        minor = values[1];
                        if(dots > 1) {
                            release = values[2];
                        }
                    }
                    project.setNewProperty("CORE", major + "." + minor +"." + release);
                    project.setNewProperty("CORE.major", major);
                    project.setNewProperty("CORE.minor", minor);
                    project.setNewProperty("CORE.release", release);
    
                ]]>
        </scriptdef>
    
        <!-- Normalize the router build number -->
        <scriptdef name="normalizeitem" language="javascript">
                <attribute name="value"/>
                <attribute name="name" />
                <![CDATA[
                    value = attributes.get("value").split("\n")[0].trim();
                    project.setNewProperty(attributes.get("name"), value);
                ]]>
        </scriptdef>
    
        <!-- input prefix, major, minor, release, routerbuild, androidbuild, sdk
             Assigns a version string and version number -->
        <scriptdef name="generateversions" language="javascript">
                <attribute name="prefix"/>
                <attribute name="major"/>
                <attribute name="minor"/>
                <attribute name="release"/>
                <attribute name="routerbuild"/>
                <attribute name="androidbuild"/>
                <attribute name="sdk"/>
                <![CDATA[
                    Major = attributes.get("major") + ".";
                    Minor = attributes.get("minor") + ".";
                    Release = attributes.get("release") +"-";
                    Routerbuild = attributes.get("routerbuild") +"_b";
                    Androidbuild = attributes.get("androidbuild") +"-API";
                    SDK = attributes.get("sdk");
                    project.setNewProperty(attributes.get("prefix") + ".full", Major + Minor + Release + Routerbuild + Androidbuild + SDK);
                    /*
                    * Android version code is an integer.
                    * So we have 31 bits.
                    * MAJOR         4 bits 0-15
                    * MINOR         8 bits 0-255
                    * RELEASE       8 bits 0-255
                    * ROUTERBUILD   7 bits 0-127
                    * ANDROIDBUILD  4 bits 0-15
                    *
                    * Note that ANDROIDBUILD is modded % 16, it will wrap,
                    * beware of that if you release multiple builds using the
                    * same ROUTERBUILD, or clear it if you update ROUTERBUILD
                    * Subtract 1 from ANDROIDBUILD since it starts at 1 after distclean.
                    */
                    iMajor = ((parseInt(Major) % 16) << 27);
                    iMinor = ((parseInt(Minor) % 256) << 19);
                    iRelease = ((parseInt(Release)% 256) << 11);
                    iRouterbuild = ((parseInt(Routerbuild) % 128) << 4);
                    iAndroidbuild = ((parseInt(Androidbuild) - 1) % 16);
                    itotal = iMajor + iMinor + iRelease + iRouterbuild + iAndroidbuild;
                    project.setNewProperty(attributes.get("prefix") + ".vercode", itotal);
                ]]>
        </scriptdef>
    
        <!-- if file 'condition' != "true" write 'properties' to file 'name' -->
        <scriptdef name="ifnotpresent" language="javascript">
            <attribute name="file" />
            <attribute name="condition" />
            <![CDATA[
                importClass(java.io.File);
                importClass(java.util.Properties);
                importClass(java.io.FileOutputStream);
                importClass(java.io.ByteArrayInputStream);
    
                doit = !attributes.get("condition").equals("true");
    
                if(doit) {
                    props = new Properties();
                    props.setProperty("build.number", "1");
                    cfg = new File(attributes.get("file"));
                    fo = new FileOutputStream(cfg);
                    props.store(fo, "AUTO-GENERATED FILE, DO NOT EDIT!");
                    fo.close();
                }
            ]]>
        </scriptdef>
        <!-- increment the build number -->
        <scriptdef name="incbuildnumber" language="javascript">
            <attribute name="file" />
            <![CDATA[
                importClass(java.io.File);
                importClass(java.util.Properties);
                importClass(java.io.FileOutputStream);
                importClass(java.io.FileInputStream);
    
                props = new Properties();
                cfg = new File(attributes.get("file"));
                fi = new FileInputStream(cfg);
                props.load(fi);
                fi.close();
                m = (parseInt(props.getProperty("build.number")) + 1).toString();
                props.setProperty("build.number", m);
                fo = new FileOutputStream(cfg);
                props.store(fo, "AUTO-GENERATED FILE, DO NOT EDIT!");
                fo.close();
            ]]>
        </scriptdef>
    
    
        <!-- Update property and xml files as needed -->
        <scriptdef name="propertyfilechecks" language="javascript">
            <attribute name="file" />
            <attribute name="condition" />
            <attribute name="propsdata" />
            <attribute name="buildfile" />
            <attribute name="mainxml" />
            <attribute name="libxml" />
            <![CDATA[
                importClass(java.io.File);
                importClass(java.util.Properties);
                importClass(java.io.FileOutputStream);
                importClass(java.io.FileInputStream);
                importClass(java.io.ByteArrayInputStream);
                importClass(java.io.InputStream);
                importClass(java.util.regex.Matcher);
                importClass(java.util.regex.Pattern);
                importClass(java.io.BufferedReader);
                importClass(java.io.BufferedWriter);
                importClass(java.lang.StringBuffer);
                importClass(java.io.InputStreamReader);
                importClass(java.io.FileWriter);
    
                doit = !attributes.get("condition").equals("true");
    
                props = new Properties();
                str = attributes.get("propsdata").toString();
                is = new ByteArrayInputStream(str.getBytes());
                props.load(is);
                cfg = new File(attributes.get("file"));
    
                if(doit) {
                    echo = project.createTask("echo");
                    echo.setMessage("Creating file='" + attributes.get("file") + "'\n" + props);
                    echo.perform();
                    fo = new FileOutputStream(cfg);
                    props.store(fo, "AUTO-GENERATED FILE, DO NOT EDIT!");
                    fo.close();
                }
    
                /* load and compare keys that start with 'last." */
                oldprops = new Properties();
                fi = new FileInputStream(cfg);
                oldprops.load(fi);
                fi.close();
                keys = props.propertyNames();
                ok = true;
                while (keys.hasMoreElements()) {
                    key = keys.nextElement();
                    if (!oldprops.containsKey(key)) {
                        ok = false;
                        break;
                    }
                    if(key.startsWith("last.")) {
                        if(!oldprops.getProperty(key).equals(props.getProperty(key))) {
                        ok = false;
                        break;
                        }
                    }
                }
                if (!ok) {
                    /* update version.props */
                    echo = project.createTask("echo");
    
                    echo.setMessage("(1)Updating file='" + attributes.get("file") + "'\n" + props);
    
                    echo.perform();
                    fo = new FileOutputStream(cfg);
                    props.store(fo, "AUTO-GENERATED FILE, DO NOT EDIT!");
                    fo.close();
                    /* reset build.number */
                    bprops = new Properties();
                    bprops.setProperty("build.number", "1");
                    echo = project.createTask("echo");
    
                    echo.setMessage("(2)Updating file='" + attributes.get("buildfile") + "'\n" + bprops);
    
                    echo.perform();
                    cfg = new File(attributes.get("buildfile"));
                    fo = new FileOutputStream(cfg);
                    bprops.store(fo, "AUTO-GENERATED FILE, DO NOT EDIT!");
                    fo.close();
    
                } else {
                    /* just update version.props */
                    echo = project.createTask("echo");
    
                    echo.setMessage("(3)Updating file='" + attributes.get("file") + "'\n" + props);
    
                    echo.perform();
                    fo = new FileOutputStream(cfg);
                    props.store(fo, "AUTO-GENERATED FILE, DO NOT EDIT!");
                    fo.close();
    
    str4d's avatar
    str4d committed
                sp1 = 'android:versionCode="[0-9]*"';
                rp1 = 'android:versionCode="' + props.getProperty("my.version.code") + '"';
                sp2 = 'android:versionName="[^"]*"';
                rp2 = 'android:versionName="' + props.getProperty("my.version.name") + '"';
    
                cfg = File(attributes.get("mainxml") + ".in");
    
                buffer = new StringBuffer();
                fi = new FileInputStream(cfg);
                reader = new BufferedReader(new InputStreamReader(fi));
                while((line = reader.readLine()) != null) {
                    rep = line.replaceAll(sp1, rp1);
                    newline = rep.replaceAll(sp2, rp2);
                    buffer.append(newline + "\n");
                }
                fi.close();
                out = new BufferedWriter(new FileWriter(attributes.get("mainxml")));
                out.write(buffer.toString());
                out.close();
                /* sed secondary manifest */
    
                cfg = File(attributes.get("libxml") + ".in");
    
                buffer = new StringBuffer();
                fi = new FileInputStream(cfg);
                reader = new BufferedReader(new InputStreamReader(fi));
                while((line = reader.readLine()) != null) {
                    rep = line.replaceAll(sp1, rp1);
                    newline = rep.replaceAll(sp2, rp2);
                    buffer.append(newline + "\n");
                }
                fi.close();
                out = new BufferedWriter(new FileWriter(attributes.get("libxml")));
                out.write(buffer.toString());
                out.close();
    
            ]]>
        </scriptdef>
    
        <!-- files of interest -->
        <property name="MANIFESTfilename" value="AndroidManifest.xml" />
    
        <property name="MANIFESTROUTERfilename" value="routerjars/AndroidManifest.xml" />
    
        <!-- Get i2p.i2p infos -->
    
        <property name="COREfilename" value="${i2psrc}/core/java/src/net/i2p/CoreVersion.java"/>
        <loadfile srcfile="${COREfilename}" property="COREfile" encoding="UTF-8" >
            <filterchain>
                <tokenfilter>
                    <containsregex pattern='^.*public.+final.+static.+String.+VERSION.*"(.*)".*' replace="\1" />
                </tokenfilter>
            </filterchain>
        </loadfile>
        <setcore value="${COREfile}" />
        <echo message="CORE `${CORE}`" />
    
        <property name="ROUTERBUILDfilename" value="${i2psrc}/router/java/src/net/i2p/router/RouterVersion.java" />
        <loadfile srcfile="${ROUTERBUILDfilename}" property="ROUTERBUILDfile" encoding="UTF-8" >
            <filterchain>
                <tokenfilter>
                    <containsregex pattern='^.*public.+final.+static.+long.+BUILD.*=[^0-9]*([0-9]+)[^0-9]+.*' replace="\1" />
                </tokenfilter>
            </filterchain>
        </loadfile>
    
        <normalizeitem name="ROUTERBUILD" value="${ROUTERBUILDfile}" />
        <echo message="ROUTERBUILD `${ROUTERBUILD}`" />
    
    
        <property name="buildversionfilename" value="scripts/build.number" />
        <available file="${buildversionfilename}" property="buildversionfilename.present" />
    
        <!-- if the file isn't there, do buildnumber to create it! -->
        <ifnotpresent file="${buildversionfilename}" condition="${buildversionfilename.present}" />
    
        <loadfile srcfile="${buildversionfilename}" property="buildversionfile" encoding="UTF-8" >
            <filterchain>
                <tokenfilter>
                    <containsregex pattern='^build.number=[^0-9]*([0-9]+)[^0-9]*.*' replace="\1" />
                </tokenfilter>
            </filterchain>
        </loadfile>
    
        <normalizeitem name="buildversion" value="${buildversionfile}" />
        <echo message="buildversion `${buildversion}`" />
    
        <split value="${target}" sep="-" prefix="gettarget"/>
        <echo message="API${gettarget.1}" />
        <!-- generate the version infos that we will want to see -->
        <generateversions prefix="zap" major="${CORE.major}"
            minor="${CORE.minor}" release="${CORE.release}"
            routerbuild="${ROUTERBUILD}" androidbuild="${buildversion}"
            sdk="${gettarget.1}"/>
    
        <echo message="checking for changes in ${zap.full}" />
    
        <property name="allversionsfilename" value="scripts/version.properties" />
        <available file="${allversionsfilename}" property="allversionsfilename.present" />
        <!-- if the file is not available, create it with the current infos -->
        <propertyfilechecks file="${allversionsfilename}" condition="${allversionsfilename.present}"
            propsdata="my.version.name=${zap.full}&#10;my.version.code=${zap.vercode}&#10;last.CORE=${CORE}&#10;last.ROUTERBUILD=${ROUTERBUILD}&#10;"
    
            buildfile="${buildversionfilename}"
    
            mainxml="${MANIFESTfilename}"
            libxml="${MANIFESTROUTERfilename}"
            />
        <loadfile srcfile="${allversionsfilename}" property="allversionsfile" encoding="UTF-8"/>
        <echo message="${allversionsfile}" />
    
        <property file="${buildversionfile}" />
        <!-- this loads my.version.code and my.version.name, and performs a copy -->
        <property file="${allversionsfilename}" />
    
        <property name="version.code" value="${my.version.code}" />
        <property name="version.name" value="${my.version.name}" />
        <echo message="version.code '${version.code}', 'version.name '${version.name}', '${my.version.name}'" />
    
    
        <!-- If we are missing any jars, we _MUST_ make them ahead of time so
    	 the build does not fail! _HOWEVER_ we must only do this if we are
    	 _BUILDING_! Apache Ant does not allow us to know what target we are
    	 about to run, because the authors believe it is 'evil' and other
    	 nonsense. So for now (so sorry!) we force build it ahead of time
    	 always, no matter what target was selected, until some better way
    	 of resolving this issue apears.
        -->
        <ant dir="routerjars" inheritall="false" useNativeBasedir="true" >
    	<target name="buildrouter" />
        </ant>
    
        <!--
             ================================================================================
             New I2P rules
             ================================================================================
        -->
    
            You must execute this target manually to force increment of the build number.
    
        -->
    
        <target name="incrementBuild" >
    
            <incbuildnumber file="${buildversionfilename}" />
    
        </target>
    
    
        <!-- overrides of those in main_rules.xml -->
    
    
    sponge's avatar
    sponge committed
        <target name="-pre-build" depends="copy-i2p-resources" >
    
            <!-- aapt messes up when resources are added or deleted, just build every time
    
            <delete dir="${gen.absolute.dir}/net" verbose="${verbose}" />
    
             -->
            <!-- screw it, do the classes too, until I add the depend class
    
            <delete dir="${out.absolute.dir}/classes/net" verbose="${verbose}" />
    
    <!--
        <target name="-pre-compile" depends="jbigi, buildrouter" />
    
        <target name="-post-compile" depends="hackcleanup" />
    -->
    
        <!--
             Creates the output directories if they don't exist yet.
    
        -->
        <target name="-dirs">
            <echo>Creating output directories if needed...</echo>
            <mkdir dir="${resource.absolute.dir}" />
            <mkdir dir="${gen.absolute.dir}" />
            <mkdir dir="${out.absolute.dir}" />
            <mkdir dir="${out.classes.absolute.dir}" />
        </target>
    
    
        <!-- some resources -->
    
        <target name="copy-i2p-resources" depends="-dirs" >
    
            <copy file="LICENSE.txt" tofile="res/raw/license_app_txt" />
            <copy file="licenses/LICENSE-Apache2.0.txt" tofile="res/raw/license_apache20_txt" />
            <copy file="${i2pbase}/installer/resources/themes/console/images/i2plogo.png" todir="res/drawable/" />
    
    	<!-- 
    	
    	No, no, no. Wrong, wrong, wrong. Static web sources should be in
            the assets directory. 
            
    
            <copy file="${i2pbase}/installer/resources/themes/console/images/outbound.png" todir="res/drawable/" />
            <copy file="${i2pbase}/installer/resources/themes/console/images/inbound.png" todir="res/drawable/" />
            <copy file="${i2pbase}/installer/resources/themes/console/light/images/header.png" todir="res/drawable/" />
    
            <copy file="${i2pbase}/installer/resources/themes/console/light/console.css" tofile="res/drawable/console_css" />
            -->
            
            <copy file="${i2pbase}/installer/resources/themes/console/images/i2plogo.png" todir="assets/themes/console/images/" />
            <copy file="${i2pbase}/installer/resources/themes/console/images/outbound.png" todir="assets/themes/console/images/" />
            <copy file="${i2pbase}/installer/resources/themes/console/images/inbound.png" todir="assets/themes/console/images/" />
            <copy file="${i2pbase}/installer/resources/themes/console/light/images/header.png" todir="assets/themes/console/light/images/" />
            <copy file="${i2pbase}/installer/resources/themes/console/light/console.css" todir="assets/themes/console/light/" />
    
    
            <copy file="${i2pbase}/installer/resources/blocklist.txt" tofile="res/raw/blocklist_txt" />
            <copy file="${i2pbase}/installer/resources/hosts.txt" tofile="res/raw/hosts_txt" />
            <copy file="${i2pbase}/licenses/LICENSE-ElGamalDSA.txt" tofile="res/raw/license_elgamaldsa_txt" />
            <copy file="${i2pbase}/licenses/LICENSE-SHA256.txt" tofile="res/raw/license_sha256_txt" />
            <copy file="${i2pbase}/licenses/LICENSE-BSD.txt" tofile="res/raw/license_bsd_txt" />
            <copy file="${i2pbase}/licenses/LICENSE-SNTP.txt" tofile="res/raw/license_sntp_txt" />
            <copy file="${i2pbase}/licenses/LICENSE-LGPLv2.1.txt" tofile="res/raw/license_lgplv2_1_txt" />
            <copy file="${i2pbase}/licenses/LICENSE-InstallCert.txt" tofile="res/raw/license_installcert_txt" />
            <copy file="${i2pbase}/licenses/LICENSE-BlockFile.txt" tofile="res/raw/license_blockfile_txt" />
            <copy file="${i2pbase}/licenses/LICENSE-GPLv2.txt" tofile="res/raw/license_gplv2_txt" />
            <copy file="${i2pbase}/licenses/LICENSE-GPLv3.txt" tofile="res/raw/license_gplv3_txt" />
            <copy file="${i2pbase}/licenses/LICENSE-LGPLv3.txt" tofile="res/raw/license_lgplv3_txt" />
    
            <copy file="${i2pbase}/licenses/LICENSE-FatCowIcons.txt" tofile="res/raw/license_fatcowicons_txt" />
    
            <copy file="${i2pbase}/licenses/LICENSE-Addressbook.txt" tofile="res/raw/license_addressbook_txt" />
    
    sponge's avatar
    sponge committed
            <delete file="res/raw/certificates_zip" />
            <zip update="true" destfile="res/raw/certificates_zip">
    
    sponge's avatar
    sponge committed
                <fileset dir="${i2pbase}/installer/resources/certificates/" />
            </zip>
    
    
        </target>
    
        <!-- install now does both -->
        <target name="reinstall" depends="install" />
    
    
            <delete dir="${jar.libs.dir}" verbose="${verbose}" />
            <delete file="res/drawable/i2plogo.png" verbose="${verbose}"/>
            <delete file="res/drawable/outbound.png" verbose="${verbose}"/>
            <delete file="res/drawable/inbound.png" verbose="${verbose}"/>
            <delete file="res/drawable/header.png" verbose="${verbose}"/>
            <delete file="res/raw/console_css" verbose="${verbose}"/>
    
    
            <delete file="assets/themes/console/images/i2plogo.png" />
            <delete file="assets/themes/console/images/outbound.png" />
            <delete file="assets/themes/console/images/inbound.png" />
            <delete file="assets/themes/console/light/images/header.png" />
            <delete file="assets/themes/console/light/console.css" />
    
    
    
            <delete file="res/raw/blocklist_txt" verbose="${verbose}" />
            <delete file="res/raw/hosts_txt" verbose="${verbose}" />
            <delete file="res/raw/license_app_txt" />
            <delete file="res/raw/license_apache20_txt" />
            <delete file="res/raw/license_elgamaldsa_txt" />
            <delete file="res/raw/license_sha256_txt" />
            <delete file="res/raw/license_bsd_txt" />
            <delete file="res/raw/license_sntp_txt" />
            <delete file="res/raw/license_lgplv2_1_txt" />
            <delete file="res/raw/license_installcert_txt" />
            <delete file="res/raw/license_blockfile_txt" />
            <delete file="res/raw/license_gplv2_txt" />
            <delete file="res/raw/license_gplv3_txt" />
            <delete file="res/raw/license_lgplv3_txt" />
    
            <delete file="res/raw/certificates_zip" />
    
        </target>
    
        <target name="distclean" depends="clean">
    
        	<ant dir="routerjars" inheritall="false" useNativeBasedir="true" >
        		<target name="distclean" />
        	</ant>
    
            <delete file="scripts/build.number" verbose="${verbose}" />
            <delete file="scripts/version.properties" verbose="${verbose}" />
    
            <delete file="AndroidManifest.xml" verbose="${verbose}" />
    
        </target>
    
        <!-- just to make it easier -->
        <target name="create-signing-keys" >
            <echo message="key store is ${key.store}" />
            <echo message="key store password is ${key.store.password}" />
            <echo message="key alias is ${key.alias}" />
            <input message="Enter common name for new key (your name): " addproperty="release.cn" />
            <fail message="You must enter a name" >
                <condition>
                    <equals arg1="${release.cn}" arg2="" />
                </condition>
            </fail>
            <input message="Enter password for new key (6 characters minimum): " addproperty="release.password" />
            <fail message="You must enter a password" >
                <condition>
                    <equals arg1="${release.password}" arg2="" />
                </condition>
            </fail>
            <echo message="Generating keys, this may take a while..." />
            <exec executable="keytool" inputstring="${release.password}${line.separator}${release.password}${line.separator}" osfamily="unix" failonerror="true">
                <arg value="-genkey" />
                <arg value="-v" />
                <arg value="-alias" />
                <arg value="${key.alias}" />
                <arg value="-keystore" />
                <arg value="${key.store}" />
                <arg value="-validity" />
                <arg value="10000" />
                <arg value="-keyalg" />
                <arg value="RSA" />
                <arg value="-keysize" />
                <arg value="4096" />
                <arg value="-storepass" />
                <arg value="${key.store.password}" />
                <arg value="-dname" />
                <arg value="cn=${release.cn}, ou=Apps, o=I2P, c=DE" />
            </exec>
            <echo message="Created keys:" />
            <exec executable="keytool" inputstring="android${line.separator}" osfamily="unix" failonerror="true">
                <arg value="-list" />
                <arg value="-v" />
                <arg value="-alias" />
                <arg value="${key.alias}" />
                <arg value="-keystore" />
                <arg value="${key.store}" />
            </exec>
            <echo message="BACK UP your key store file ${key.store} and your password!" />
        </target>
    
        <target name="verifyKeystore" >
            <available file="${key.store}" property="keystore.present" />
            <fail message="You must first create a keystore and keys with 'ant create-signing-keys'" >
                <condition>
                    <not>
                        <isset property="keystore.present" />
                    </not>
                </condition>
            </fail>
        </target>
    
        <target name="verifyWorkspace" >
            <echo message="Everything is checked in, right? Let's be sure:" />
            <exec executable="mtn" failonerror="true">
                <arg value="st" />
            </exec>
            <echo message="If there are any modified files above, stop now!" />
            <echo message="(except AndroidManifest.xml)" />
        </target>
    
        <target name="verify" depends="verifyKeystore, verifyWorkspace, release" >
            <exec executable="jarsigner" osfamily="unix" failonerror="true">
                <arg value="-verify" />
                <arg value="-verbose" />
                <arg value="-certs" />
                <arg value="${out.release.file}" />
            </exec>
            <echo message="" />
            <echo message="Release file is ${out.release.file}" />
            <echo message="Android version name: ${my.version.name}" />
            <echo message="Android version code: ${my.version.code}" />
            <echo message="File size:" />
            <exec executable="ls" failonerror="true">
                <arg value="-l" />
                <arg value="${out.release.file}" />
            </exec>
            <echo message="SHA256 sum:" />
            <exec executable="sha256sum" failonerror="true">
                <arg value="${out.release.file}" />
            </exec>
            <echo message="Don't forget to mtn ci AndroidManifest.xml" />
            <echo message="Don't forget to mtn tag w: android-${my.version.name}" />
            <copy file="${out.release.file}" tofile="I2PAndroid-${my.version.name}.apk" />
            <echo message="Release file copied to I2PAndroid-${my.version.name}.apk" />
        </target>
    </project>