Explorar o código

Scripts: simpler tar format (#1871)

* scriptsL simpler tar format
* scripts: shorter names for files in update bundle
* scripts: limiting max OTA package dir name length to 80
* scripts: resource bundle: checks for file name length
* scripts: made resource packing errors critical
hedger %!s(int64=3) %!d(string=hai) anos
pai
achega
8fdee1e460
Modificáronse 3 ficheiros con 34 adicións e 11 borrados
  1. 1 1
      scripts/flipper/assets/copro.py
  2. 5 1
      scripts/sconsdist.py
  3. 28 9
      scripts/update.py

+ 1 - 1
scripts/flipper/assets/copro.py

@@ -60,7 +60,7 @@ class Copro:
         array.append({"name": filename, "sha256": file_sha256(source_file), **kwargs})
 
     def bundle(self, output_file, stack_file_name, stack_type, stack_addr=None):
-        self.output_tar = tarfile.open(output_file, "w:gz")
+        self.output_tar = tarfile.open(output_file, "w:gz", format=tarfile.USTAR_FORMAT)
 
         stack_file = os.path.join(self.mcu_copro, stack_file_name)
         # Form Manifest

+ 5 - 1
scripts/sconsdist.py

@@ -20,6 +20,7 @@ class ProjectDir:
 
 class Main(App):
     DIST_FILE_PREFIX = "flipper-z-"
+    DIST_FOLDER_MAX_NAME_LENGTH = 80
 
     def init(self):
         self.subparsers = self.parser.add_subparsers(help="sub-command help")
@@ -129,7 +130,9 @@ class Main(App):
         )
 
         if self.args.version:
-            bundle_dir_name = f"{self.target}-update-{self.args.suffix}"
+            bundle_dir_name = f"{self.target}-update-{self.args.suffix}"[
+                : self.DIST_FOLDER_MAX_NAME_LENGTH
+            ]
             bundle_dir = join(self.output_dir_path, bundle_dir_name)
             bundle_args = [
                 "generate",
@@ -170,6 +173,7 @@ class Main(App):
                     ),
                     "w:gz",
                     compresslevel=9,
+                    format=tarfile.USTAR_FORMAT,
                 ) as tar:
                     tar.add(bundle_dir, arcname=bundle_dir_name)
 

+ 28 - 9
scripts/update.py

@@ -22,6 +22,7 @@ class Main(App):
     RESOURCE_TAR_MODE = "w:"
     RESOURCE_TAR_FORMAT = tarfile.USTAR_FORMAT
     RESOURCE_FILE_NAME = "resources.tar"
+    RESOURCE_ENTRY_NAME_MAX_LENGTH = 100
 
     WHITELISTED_STACK_TYPES = set(
         map(
@@ -76,9 +77,9 @@ class Main(App):
         self.parser_generate.set_defaults(func=self.generate)
 
     def generate(self):
-        stage_basename = basename(self.args.stage)
-        dfu_basename = basename(self.args.dfu)
-        radiobin_basename = basename(self.args.radiobin)
+        stage_basename = "updater.bin"  # used to be basename(self.args.stage)
+        dfu_basename = "firmware.dfu"  # used to be basename(self.args.dfu)
+        radiobin_basename = "radio.bin"  # used to be basename(self.args.radiobin)
         resources_basename = ""
 
         radio_version = 0
@@ -120,9 +121,10 @@ class Main(App):
             )
         if self.args.resources:
             resources_basename = self.RESOURCE_FILE_NAME
-            self.package_resources(
+            if not self.package_resources(
                 self.args.resources, join(self.args.directory, resources_basename)
-            )
+            ):
+                return 3
 
         if not self.layout_check(dfu_size, radio_addr):
             self.logger.warn("Memory layout looks suspicious")
@@ -199,11 +201,28 @@ class Main(App):
             "Please confirm that you REALLY want to do that with --I-understand-what-I-am-doing=yes"
         )
 
+    def _tar_filter(self, tarinfo: tarfile.TarInfo):
+        if len(tarinfo.name) > self.RESOURCE_ENTRY_NAME_MAX_LENGTH:
+            self.logger.error(
+                f"Cannot package resource: name '{tarinfo.name}' too long"
+            )
+            raise ValueError("Resource name too long")
+        return tarinfo
+
     def package_resources(self, srcdir: str, dst_name: str):
-        with tarfile.open(
-            dst_name, self.RESOURCE_TAR_MODE, format=self.RESOURCE_TAR_FORMAT
-        ) as tarball:
-            tarball.add(srcdir, arcname="")
+        try:
+            with tarfile.open(
+                dst_name, self.RESOURCE_TAR_MODE, format=self.RESOURCE_TAR_FORMAT
+            ) as tarball:
+                tarball.add(
+                    srcdir,
+                    arcname="",
+                    filter=self._tar_filter,
+                )
+            return True
+        except ValueError as e:
+            self.logger.error(f"Cannot package resources: {e}")
+            return False
 
     @staticmethod
     def copro_version_as_int(coprometa, stacktype):