diff --git a/Android.bp b/Android.bp index d1b8f0022..cc28c9893 100644 --- a/Android.bp +++ b/Android.bp @@ -4,6 +4,7 @@ subdirs = [ "cmd/*", "fs", "finder", + "jar", "third_party/zip", "ui/*", ] diff --git a/cmd/zip2zip/Android.bp b/cmd/zip2zip/Android.bp index 476be4f24..64202193a 100644 --- a/cmd/zip2zip/Android.bp +++ b/cmd/zip2zip/Android.bp @@ -14,7 +14,10 @@ blueprint_go_binary { name: "zip2zip", - deps: ["android-archive-zip"], + deps: [ + "android-archive-zip", + "soong-jar", + ], srcs: [ "zip2zip.go", ], diff --git a/cmd/zip2zip/zip2zip.go b/cmd/zip2zip/zip2zip.go index 815059c90..f48d458b8 100644 --- a/cmd/zip2zip/zip2zip.go +++ b/cmd/zip2zip/zip2zip.go @@ -24,6 +24,7 @@ import ( "strings" "time" + "android/soong/jar" "android/soong/third_party/zip" ) @@ -178,37 +179,7 @@ func zip2zip(reader *zip.Reader, writer *zip.Writer, sortGlobs, sortJava, setTim } func jarSort(files []pair) { - // Treats trailing * as a prefix match - match := func(pattern, name string) bool { - if strings.HasSuffix(pattern, "*") { - return strings.HasPrefix(name, strings.TrimSuffix(pattern, "*")) - } else { - return name == pattern - } - } - - var jarOrder = []string{ - "META-INF/", - "META-INF/MANIFEST.MF", - "META-INF/*", - "*", - } - - index := func(name string) int { - for i, pattern := range jarOrder { - if match(pattern, name) { - return i - } - } - panic(fmt.Errorf("file %q did not match any pattern", name)) - } - sort.SliceStable(files, func(i, j int) bool { - diff := index(files[i].newName) - index(files[j].newName) - if diff == 0 { - return files[i].newName < files[j].newName - } else { - return diff < 0 - } + return jar.EntryNamesLess(files[i].newName, files[j].newName) }) } diff --git a/jar/Android.bp b/jar/Android.bp new file mode 100644 index 000000000..23ad53681 --- /dev/null +++ b/jar/Android.bp @@ -0,0 +1,22 @@ +// Copyright 2017 Google Inc. All rights reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +bootstrap_go_package { + name: "soong-jar", + pkgPath: "android/soong/jar", + srcs: [ + "jar.go", + ], +} + diff --git a/jar/jar.go b/jar/jar.go new file mode 100644 index 000000000..d8f063c98 --- /dev/null +++ b/jar/jar.go @@ -0,0 +1,55 @@ +// Copyright 2017 Google Inc. All rights reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +package jar + +import ( + "fmt" + "strings" +) + +// EntryNamesLess tells whether should precede in +// the order of files with a .jar +func EntryNamesLess(filepathA string, filepathB string) (less bool) { + diff := index(filepathA) - index(filepathB) + if diff == 0 { + return filepathA < filepathB + } + return diff < 0 +} + +// Treats trailing * as a prefix match +func patternMatch(pattern, name string) bool { + if strings.HasSuffix(pattern, "*") { + return strings.HasPrefix(name, strings.TrimSuffix(pattern, "*")) + } else { + return name == pattern + } +} + +var jarOrder = []string{ + "META-INF/", + "META-INF/MANIFEST.MF", + "META-INF/*", + "*", +} + +func index(name string) int { + for i, pattern := range jarOrder { + if patternMatch(pattern, name) { + return i + } + } + panic(fmt.Errorf("file %q did not match any pattern", name)) +}