Backed out 7 changesets (bug 1501878) for breaking win partial generation nightlies a=backout
authorAndreea Pavel <apavel@mozilla.com>
Sat, 17 Nov 2018 18:37:39 +0200
changeset 503349 94debc6ca20b5f9e8d2e617430673dd94139c4e9
parent 503348 d4991991fb9823f3155097d6e0ae44aba683f71d
child 503353 a92c330bac8bce0c51099d630349aecbb71d7c35
push id10290
push userffxbld-merge
push dateMon, 03 Dec 2018 16:23:23 +0000
treeherdermozilla-beta@700bed2445e6 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersbackout
bugs1501878
milestone65.0a1
backs out00f109437e82f6e9a350911573cbe11a5bafcfed
f1843fdd4c0fa13722f5fe7ab7b73d5fdc2ad3ef
af0ea80f7b081a64d964e762b06b940e3c4f1b3f
01311f87d2875954fd7cfb347cf7d123974c3a1f
4e2dc6c23463e976ba90cf2113eea9dbfcb89fcb
050c4bba5d710059175026e9f0185e795fcdfc28
9198c5a03b592b0f4da406d849951cac152fe8b3
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Backed out 7 changesets (bug 1501878) for breaking win partial generation nightlies a=backout Backed out changeset 00f109437e82 (bug 1501878) Backed out changeset f1843fdd4c0f (bug 1501878) Backed out changeset af0ea80f7b08 (bug 1501878) Backed out changeset 01311f87d287 (bug 1501878) Backed out changeset 4e2dc6c23463 (bug 1501878) Backed out changeset 050c4bba5d71 (bug 1501878) Backed out changeset 9198c5a03b59 (bug 1501878)
taskcluster/ci/beetmover-repackage/kind.yml
taskcluster/ci/config.yml
taskcluster/ci/mar-signing-l10n/kind.yml
taskcluster/ci/mar-signing/kind.yml
taskcluster/ci/partials-signing/kind.yml
taskcluster/ci/partials/kind.yml
taskcluster/ci/repackage-signing-l10n/kind.yml
taskcluster/ci/repackage-signing/kind.yml
taskcluster/docs/attributes.rst
taskcluster/docs/kinds.rst
taskcluster/docs/parameters.rst
taskcluster/taskgraph/actions/release_promotion.py
taskcluster/taskgraph/decision.py
taskcluster/taskgraph/loader/multi_dep.py
taskcluster/taskgraph/parameters.py
taskcluster/taskgraph/target_tasks.py
taskcluster/taskgraph/transforms/balrog_submit.py
taskcluster/taskgraph/transforms/beetmover_repackage.py
taskcluster/taskgraph/transforms/beetmover_repackage_l10n.py
taskcluster/taskgraph/transforms/mar_signing.py
taskcluster/taskgraph/transforms/partials.py
taskcluster/taskgraph/transforms/partials_signing.py
taskcluster/taskgraph/transforms/per_platform_dummy.py
taskcluster/taskgraph/transforms/release_deps.py
taskcluster/taskgraph/transforms/release_generate_checksums_beetmover.py
taskcluster/taskgraph/transforms/release_snap_push.py
taskcluster/taskgraph/transforms/repackage_signing.py
taskcluster/taskgraph/util/attributes.py
taskcluster/taskgraph/util/verify.py
--- a/taskcluster/ci/beetmover-repackage/kind.yml
+++ b/taskcluster/ci/beetmover-repackage/kind.yml
@@ -19,22 +19,20 @@ kind-dependencies:
     - repackage-signing
     - nightly-l10n
     - nightly-l10n-signing
     - repackage-l10n
     - repackage-signing-l10n
     - partials
     - partials-signing
     - repackage-signing-msi
-    - mar-signing
-    - mar-signing-l10n
 
 primary-dependency:
-    - repackage
-    - repackage-l10n
+    - repackage-signing-l10n
+    - repackage-signing
 
 only-for-build-platforms:
     - linux-nightly/opt
     - linux64-nightly/opt
     - macosx64-nightly/opt
     - win32-nightly/opt
     - win64-nightly/opt
     - linux-devedition-nightly/opt
--- a/taskcluster/ci/config.yml
+++ b/taskcluster/ci/config.yml
@@ -72,17 +72,16 @@ treeherder:
         'TW64': 'Toolchain builds for Windows 64-bits'
         'WMC32': 'MinGW-Clang builds for Windows 32-bits'
         'WMC64': 'MinGW-Clang builds for Windows 64-bits'
         'Searchfox': 'Searchfox builds'
         'SM': 'Spidermonkey builds'
         'pub': 'APK publishing'
         'p': 'Partial generation'
         'ps': 'Partials signing'
-        'ms': 'Complete MAR signing'
         'Rel': 'Release promotion'
         'Snap': 'Snap image generation'
         'langpack': 'Langpack sigatures and uploads'
         'TPS': 'Sync tests'
         'UV': 'Update verify'
         'pipfu': 'pipfile update'
 
 index:
deleted file mode 100644
--- a/taskcluster/ci/mar-signing-l10n/kind.yml
+++ /dev/null
@@ -1,33 +0,0 @@
-# This Source Code Form is subject to the terms of the Mozilla Public
-# License, v. 2.0. If a copy of the MPL was not distributed with this
-# file, You can obtain one at http://mozilla.org/MPL/2.0/.
-
-loader: taskgraph.loader.single_dep:loader
-
-transforms:
-    - taskgraph.transforms.name_sanity:transforms
-    - taskgraph.transforms.mar_signing:transforms
-    - taskgraph.transforms.task:transforms
-
-kind-dependencies:
-    - repackage-l10n
-
-only-for-build-platforms:
-    - linux-nightly/opt
-    - linux-devedition-nightly/opt
-    - linux64-nightly/opt
-    - linux64-devedition-nightly/opt
-    - linux64-asan-reporter-nightly/opt
-    - macosx64-nightly/opt
-    - macosx64-devedition-nightly/opt
-    - win32-nightly/opt
-    - win32-devedition-nightly/opt
-    - win64-nightly/opt
-    - win64-devedition-nightly/opt
-
-job-template:
-    shipping-phase: promote
-    treeherder-group: ms
-    description-suffix: 'mar signing'
-    required_signoffs:
-        - mar-signing
deleted file mode 100644
--- a/taskcluster/ci/mar-signing/kind.yml
+++ /dev/null
@@ -1,35 +0,0 @@
-# This Source Code Form is subject to the terms of the Mozilla Public
-# License, v. 2.0. If a copy of the MPL was not distributed with this
-# file, You can obtain one at http://mozilla.org/MPL/2.0/.
-
-loader: taskgraph.loader.single_dep:loader
-
-transforms:
-    - taskgraph.transforms.name_sanity:transforms
-    - taskgraph.transforms.mar_signing:transforms
-    - taskgraph.transforms.task:transforms
-
-kind-dependencies:
-    - repackage
-
-only-for-build-platforms:
-    - linux-nightly/opt
-    - linux-devedition-nightly/opt
-    - linux64-nightly/opt
-    - linux64-devedition-nightly/opt
-    - linux64-asan-reporter-nightly/opt
-    - macosx64-nightly/opt
-    - macosx64-devedition-nightly/opt
-    - win32-nightly/opt
-    - win32-devedition-nightly/opt
-    - win64-nightly/opt
-    - win64-devedition-nightly/opt
-    - linux64-asan-reporter-nightly/opt
-    - win64-asan-reporter-nightly/opt
-
-job-template:
-    shipping-phase: promote
-    treeherder-group: ms
-    description-suffix: 'mar signing'
-    required_signoffs:
-        - mar-signing
--- a/taskcluster/ci/partials-signing/kind.yml
+++ b/taskcluster/ci/partials-signing/kind.yml
@@ -1,20 +1,16 @@
 # This Source Code Form is subject to the terms of the Mozilla Public
 # License, v. 2.0. If a copy of the MPL was not distributed with this
 # file, You can obtain one at http://mozilla.org/MPL/2.0/.
 
 loader: taskgraph.loader.single_dep:loader
 
 transforms:
   - taskgraph.transforms.name_sanity:transforms
-  - taskgraph.transforms.mar_signing:transforms
+  - taskgraph.transforms.partials_signing:transforms
   - taskgraph.transforms.task:transforms
 
 kind-dependencies:
   - partials
 
 job-template:
   shipping-phase: promote
-  treeherder-group: ps
-  description-suffix: 'partial signing'
-  required_signoffs:
-    - mar-signing
--- a/taskcluster/ci/partials/kind.yml
+++ b/taskcluster/ci/partials/kind.yml
@@ -5,18 +5,18 @@
 loader: taskgraph.loader.single_dep:loader
 
 transforms:
    - taskgraph.transforms.name_sanity:transforms
    - taskgraph.transforms.partials:transforms
    - taskgraph.transforms.task:transforms
 
 kind-dependencies:
-   - repackage
-   - repackage-l10n
+   - repackage-signing
+   - repackage-signing-l10n
 
 only-for-attributes:
    - nightly
 
 only-for-build-platforms:
    - macosx64-nightly/opt
    - macosx64-devedition-nightly/opt
    - win32-nightly/opt
--- a/taskcluster/ci/repackage-signing-l10n/kind.yml
+++ b/taskcluster/ci/repackage-signing-l10n/kind.yml
@@ -9,15 +9,22 @@ transforms:
    - taskgraph.transforms.repackage_signing:transforms
    - taskgraph.transforms.repackage_routes:transforms
    - taskgraph.transforms.task:transforms
 
 kind-dependencies:
    - repackage-l10n
 
 only-for-build-platforms:
+   - linux-nightly/opt
+   - linux-devedition-nightly/opt
+   - linux64-nightly/opt
+   - linux64-devedition-nightly/opt
+   - linux64-asan-reporter-nightly/opt
+   - macosx64-nightly/opt
+   - macosx64-devedition-nightly/opt
    - win32-nightly/opt
    - win32-devedition-nightly/opt
    - win32/opt
    - win64-nightly/opt
    - win64-devedition-nightly/opt
    - win64/opt
    - win64-asan-reporter-nightly/opt
--- a/taskcluster/ci/repackage-signing/kind.yml
+++ b/taskcluster/ci/repackage-signing/kind.yml
@@ -9,15 +9,22 @@ transforms:
    - taskgraph.transforms.repackage_signing:transforms
    - taskgraph.transforms.repackage_routes:transforms
    - taskgraph.transforms.task:transforms
 
 kind-dependencies:
    - repackage
 
 only-for-build-platforms:
+   - linux-nightly/opt
+   - linux-devedition-nightly/opt
+   - linux64-nightly/opt
+   - linux64-devedition-nightly/opt
+   - linux64-asan-reporter-nightly/opt
+   - macosx64-nightly/opt
+   - macosx64-devedition-nightly/opt
    - win32-nightly/opt
    - win32-devedition-nightly/opt
    - win32/opt
    - win64-nightly/opt
    - win64-devedition-nightly/opt
    - win64/opt
    - win64-asan-reporter-nightly/opt
--- a/taskcluster/docs/attributes.rst
+++ b/taskcluster/docs/attributes.rst
@@ -261,15 +261,8 @@ cache_digest
 Some tasks generate artifacts that are cached between pushes. This is the unique string used
 to identify the current version of the artifacts. See :py:mod:`taskgraph.util.cached_task`.
 
 cache_type
 ==========
 Some tasks generate artifacts that are cached between pushes. This is the type of cache that is
 used for the this task. See :py:mod:`taskgraph.util.cached_task`.
 
-required_signoffs
-=================
-A list of release signoffs that this kind requires, should the release also
-require these signoffs. For example, ``mar-signing`` signoffs may be required
-by some releases in the future; for any releases that require ``mar-signing``
-signoffs, the kinds that also require that signoff are marked with this
-attribute.
--- a/taskcluster/docs/kinds.rst
+++ b/taskcluster/docs/kinds.rst
@@ -443,29 +443,23 @@ and this task would package that up as a
 
 repackage-l10n
 --------------
 Repackage-L10n is a ```Repackage``` task split up to be suitable for use after l10n repacks.
 
 
 repackage-signing
 -----------------
-Repackage-signing take the repackaged installers (windows) and signs them.
+Repackage-signing take the repackaged installers (windows) and update packaging (with
+the signed internal bits) and signs them.
 
 repackage-signing-l10n
 ----------------------
-Repackage-signing-l10n take the repackaged installers (windows) and signs them for localized versions.
-
-mar-signing
------------
-Mar-signing takes the complete update MARs and signs them.
-
-mar-signing-l10n
-----------------
-Mar-signing-l10n takes the complete update MARs and signs them for localized versions.
+Repackage-signing take the repackaged installers (windows) and update packaging (with
+the signed internal bits) and signs them for localized versions.
 
 repackage-msi
 -------------
 Repackage-msi takes the signed full installer and produces an msi installer (that wraps the full installer)
 Using the ```./mach repackage``` command
 
 repackage-signing-msi
 ---------------------
--- a/taskcluster/docs/parameters.rst
+++ b/taskcluster/docs/parameters.rst
@@ -171,22 +171,16 @@ Release Promotion
    The build number for partner repacks. We sometimes have multiple partner build numbers per release build number; this parameter lets us bump them independently. Defaults to 1.
 
 ``release_enable_emefree``
    Boolean which controls repacking vanilla Firefox builds into EME-free builds.
 
 ``release_product``
    The product that is being released.
 
-``required_signoffs``
-   A list of signoffs that are required for this release promotion flavor. If specified, and if the corresponding `signoff_urls` url isn't specified, tasks that require these signoffs will not be scheduled.
-
-``signoff_urls``
-   A dictionary of signoff keys to url values. These are the urls marking the corresponding ``required_signoffs`` as signed off.
-
 Comm Push Information
 ---------------------
 
 These parameters correspond to the repository and revision of the comm-central
 repository to checkout. Their meaning is the same as the corresponding
 parameters for the gecko repository above. They are optional, but if any of
 them are specified, they must all be specified.
 
--- a/taskcluster/taskgraph/actions/release_promotion.py
+++ b/taskcluster/taskgraph/actions/release_promotion.py
@@ -24,51 +24,27 @@ from taskgraph.util.partners import (
     get_token
 )
 from taskgraph.taskgraph import TaskGraph
 from taskgraph.decision import taskgraph_decision
 from taskgraph.parameters import Parameters
 from taskgraph.util.attributes import RELEASE_PROMOTION_PROJECTS
 
 
-RELEASE_PROMOTION_SIGNOFFS = ('mar-signing', )
-
-
 def is_release_promotion_available(parameters):
     return parameters['project'] in RELEASE_PROMOTION_PROJECTS
 
 
 def get_partner_config(partner_url_config, github_token):
     partner_config = {}
     for kind, url in partner_url_config.items():
         partner_config[kind] = get_partner_config_by_url(url, kind, github_token)
     return partner_config
 
 
-def get_signoff_properties():
-    props = {}
-    for signoff in RELEASE_PROMOTION_SIGNOFFS:
-        props[signoff] = {
-            'type': 'string',
-        }
-    return props
-
-
-def get_required_signoffs(input, parameters):
-    input_signoffs = set(input.get('required_signoffs', []))
-    params_signoffs = set(parameters['required_signoffs'] or [])
-    return sorted(list(input_signoffs | params_signoffs))
-
-
-def get_signoff_urls(input, parameters):
-    signoff_urls = parameters['signoff_urls']
-    signoff_urls.update(input.get('signoff_urls', {}))
-    return signoff_urls
-
-
 def get_flavors(graph_config, param):
     """
     Get all flavors with the given parameter enabled.
     """
     promotion_flavors = graph_config['release-promotion']['flavors']
     return sorted([
         flavor for (flavor, config) in promotion_flavors.items()
         if config.get(param, False)
@@ -216,29 +192,16 @@ def get_flavors(graph_config, param):
                 'properties': {},
                 'additionalProperties': True,
             },
             'release_enable_emefree': {
                 'type': 'boolean',
                 'default': False,
                 'description': ('Toggle for creating EME-free repacks'),
             },
-            'required_signoffs': {
-                'type': 'array',
-                'description': ('The flavor of release promotion to perform.'),
-                'items': {
-                    'enum': RELEASE_PROMOTION_SIGNOFFS,
-                }
-            },
-            'signoff_urls': {
-                'type': 'object',
-                'default': {},
-                'additionalProperties': False,
-                'properties': get_signoff_properties(),
-            },
         },
         "required": ['release_promotion_flavor', 'build_number'],
     }
 )
 def release_promotion_action(parameters, graph_config, input, task_group_id, task_id, task):
     release_promotion_flavor = input['release_promotion_flavor']
     promotion_config = graph_config['release-promotion']['flavors'][release_promotion_flavor]
     release_history = {}
@@ -340,15 +303,12 @@ def release_promotion_action(parameters,
         parameters['release_partner_build_number'] = input['release_partner_build_number']
 
     if partner_config:
         parameters['release_partner_config'] = fix_partner_config(partner_config)
 
     if input['version']:
         parameters['version'] = input['version']
 
-    parameters['required_signoffs'] = get_required_signoffs(input, parameters)
-    parameters['signoff_urls'] = get_signoff_urls(input, parameters)
-
     # make parameters read-only
     parameters = Parameters(**parameters)
 
     taskgraph_decision({'root': graph_config.root_dir}, parameters=parameters)
--- a/taskcluster/taskgraph/decision.py
+++ b/taskcluster/taskgraph/decision.py
@@ -233,18 +233,16 @@ def get_decision_parameters(config, opti
     parameters['release_type'] = ''
     parameters['release_eta'] = ''
     parameters['release_enable_partners'] = False
     parameters['release_partners'] = []
     parameters['release_partner_config'] = {}
     parameters['release_partner_build_number'] = 1
     parameters['release_enable_emefree'] = False
     parameters['release_product'] = None
-    parameters['required_signoffs'] = []
-    parameters['signoff_urls'] = {}
     parameters['try_mode'] = None
     parameters['try_task_config'] = None
     parameters['try_options'] = None
 
     # owner must be an email, but sometimes (e.g., for ffxbld) it is not, in which
     # case, fake it
     if '@' not in parameters['owner']:
         parameters['owner'] += '@noreply.mozilla.org'
--- a/taskcluster/taskgraph/loader/multi_dep.py
+++ b/taskcluster/taskgraph/loader/multi_dep.py
@@ -4,17 +4,16 @@
 
 from __future__ import absolute_import, print_function, unicode_literals
 
 import copy
 
 from voluptuous import Required
 
 from ..task import Task
-from ..util.attributes import sorted_unique_list
 from ..util.schema import Schema
 
 schema = Schema({
     Required('primary-dependency', 'primary dependency task'): Task,
     Required(
         'dependent-tasks',
         'dictionary of dependent tasks, keyed by kind',
     ): {basestring: Task},
@@ -62,21 +61,16 @@ def loader(kind, path, config, params, l
             job.update(copy.deepcopy(job_template))
         # copy shipping_product from upstream
         product = job['primary-dependency'].attributes.get(
             'shipping_product',
             job['primary-dependency'].task.get('shipping-product')
         )
         if product:
             job.setdefault('shipping-product', product)
-        job.setdefault('attributes', {})['required_signoffs'] = sorted_unique_list(
-            *[task.attributes.get('required_signoffs', [])
-              for task in dep_tasks.values()
-              ]
-        )
 
         yield job
 
 
 def group_tasks(config, tasks):
     group_by_fn = GROUP_BY_MAP[config['group-by']]
 
     groups = group_by_fn(config, tasks)
--- a/taskcluster/taskgraph/parameters.py
+++ b/taskcluster/taskgraph/parameters.py
@@ -73,18 +73,16 @@ PARAMETERS = {
     'release_enable_partners': False,
     'release_eta': '',
     'release_history': {},
     'release_partners': None,
     'release_partner_config': None,
     'release_partner_build_number': 1,
     'release_type': 'nightly',
     'release_product': None,
-    'required_signoffs': [],
-    'signoff_urls': {},
     'target_tasks_method': 'default',
     'try_mode': None,
     'try_options': None,
     'try_task_config': None,
     'version': get_version(),
 }
 
 COMM_PARAMETERS = {
--- a/taskcluster/taskgraph/target_tasks.py
+++ b/taskcluster/taskgraph/target_tasks.py
@@ -80,24 +80,16 @@ def filter_release_tasks(task, parameter
             return False
 
     if task.attributes.get('shipping_phase') not in (None, 'build'):
         return False
 
     return True
 
 
-def filter_out_missing_signoffs(task, parameters):
-    for signoff in parameters['required_signoffs']:
-        if signoff not in parameters['signoff_urls'] and \
-           signoff in task.attributes.get('required_signoffs', []):
-            return False
-    return True
-
-
 def standard_filter(task, parameters):
     return all(
         filter_func(task, parameters) for filter_func in
         (filter_out_cron, filter_for_project, filter_for_hg_branch)
     )
 
 
 def _try_task_config(full_task_graph, parameters, graph_config):
@@ -323,36 +315,31 @@ def target_tasks_promote_desktop(full_ta
         if task.attributes.get('shipping_product') != parameters['release_product']:
             return False
 
         # 'secondary' balrog/update verify/final verify tasks only run for RCs
         if parameters.get('release_type') != 'release-rc':
             if 'secondary' in task.kind:
                 return False
 
-        if not filter_out_missing_signoffs(task, parameters):
-            return False
-
         if task.attributes.get('shipping_phase') == 'promote':
             return True
 
     return [l for l, t in full_task_graph.tasks.iteritems() if filter(t)]
 
 
 @_target_task('push_desktop')
 def target_tasks_push_desktop(full_task_graph, parameters, graph_config):
     """Select the set of tasks required to push a build of desktop to cdns.
     Previous build deps will be optimized out via action task."""
     filtered_for_candidates = target_tasks_promote_desktop(
         full_task_graph, parameters, graph_config,
     )
 
     def filter(task):
-        if not filter_out_missing_signoffs(task, parameters):
-            return False
         # Include promotion tasks; these will be optimized out
         if task.label in filtered_for_candidates:
             return True
         if task.attributes.get('shipping_product') == parameters['release_product'] and \
                 task.attributes.get('shipping_phase') == 'push':
             return True
 
     return [l for l, t in full_task_graph.tasks.iteritems() if filter(t)]
@@ -371,18 +358,16 @@ def target_tasks_ship_desktop(full_task_
         )
     else:
         # ship_firefox runs after `push`; include all push tasks.
         filtered_for_candidates = target_tasks_push_desktop(
             full_task_graph, parameters, graph_config,
         )
 
     def filter(task):
-        if not filter_out_missing_signoffs(task, parameters):
-            return False
         # Include promotion tasks; these will be optimized out
         if task.label in filtered_for_candidates:
             return True
         if task.attributes.get('shipping_product') != parameters['release_product'] or \
                 task.attributes.get('shipping_phase') != 'ship':
             return False
 
         if 'secondary' in task.kind:
--- a/taskcluster/taskgraph/transforms/balrog_submit.py
+++ b/taskcluster/taskgraph/transforms/balrog_submit.py
@@ -33,18 +33,16 @@ balrog_description_schema = schema.exten
     # unique label to describe this balrog task, defaults to balrog-{dep.label}
     Optional('label'): basestring,
 
     # treeherder is allowed here to override any defaults we use for beetmover.  See
     # taskcluster/taskgraph/transforms/task.py for the schema details, and the
     # below transforms for defaults of various values.
     Optional('treeherder'): task_description_schema['treeherder'],
 
-    Optional('attributes'): task_description_schema['attributes'],
-
     # Shipping product / phase
     Optional('shipping-product'): task_description_schema['shipping-product'],
     Optional('shipping-phase'): task_description_schema['shipping-phase'],
 })
 
 
 @transforms.add
 def validate(config, jobs):
--- a/taskcluster/taskgraph/transforms/beetmover_repackage.py
+++ b/taskcluster/taskgraph/transforms/beetmover_repackage.py
@@ -125,28 +125,26 @@ UPSTREAM_ARTIFACT_SIGNED_PATHS = _compil
 UPSTREAM_ARTIFACT_REPACKAGE_PATHS = [
     'target.dmg',
 ]
 # Until bug 1331141 is fixed, if you are adding any new artifacts here that
 # need to be transfered to S3, please be aware you also need to follow-up
 # with a beetmover patch in https://github.com/mozilla-releng/beetmoverscript/.
 # See example in bug 1348286
 UPSTREAM_ARTIFACT_SIGNED_REPACKAGE_PATHS = [
+    'target.complete.mar',
+    'target.bz2.complete.mar',
     'target.installer.exe',
     'target.stub-installer.exe',
 ]
 
 UPSTREAM_ARTIFACT_SIGNED_MSI_PATHS = [
     'target.installer.msi',
 ]
 
-UPSTREAM_ARTIFACT_SIGNED_MAR_PATHS = [
-    'target.complete.mar',
-]
-
 # Voluptuous uses marker objects as dictionary *keys*, but they are not
 # comparable, so we cast all of the keys back to regular strings
 task_description_schema = {str(k): v for k, v in task_description_schema.schema.iteritems()}
 
 transforms = TransformSequence()
 
 # shortcut for a string where task references are allowed
 taskref_or_string = Any(
@@ -160,18 +158,16 @@ beetmover_description_schema = schema.ex
     # unique label to describe this beetmover task, defaults to {dep.label}-beetmover
     Required('label'): basestring,
 
     # treeherder is allowed here to override any defaults we use for beetmover.  See
     # taskcluster/taskgraph/transforms/task.py for the schema details, and the
     # below transforms for defaults of various values.
     Optional('treeherder'): task_description_schema['treeherder'],
 
-    Optional('attributes'): task_description_schema['attributes'],
-
     # locale is passed only for l10n beetmoving
     Optional('locale'): basestring,
     Required('shipping-phase'): task_description_schema['shipping-phase'],
     # Optional until we fix asan (run_on_projects?)
     Optional('shipping-product'): task_description_schema['shipping-product'],
 })
 
 
@@ -206,43 +202,39 @@ def make_task_description(config, jobs):
                 locale=attributes.get('locale', 'en-US'),
                 build_platform=attributes.get('build_platform'),
                 build_type=attributes.get('build_type')
             )
         )
 
         upstream_deps = job['dependent-tasks']
 
+        # TODO fix the upstreamArtifact generation to not need this?
         signing_name = "build-signing"
         build_name = "build"
         repackage_name = "repackage"
         repackage_signing_name = "repackage-signing"
         msi_signing_name = "repackage-signing-msi"
-        mar_signing_name = "mar-signing"
         if job.get('locale'):
             signing_name = "nightly-l10n-signing"
             build_name = "nightly-l10n"
             repackage_name = "repackage-l10n"
             repackage_signing_name = "repackage-signing-l10n"
-            mar_signing_name = "mar-signing-l10n"
         dependencies = {
             "build": upstream_deps[build_name],
             "repackage": upstream_deps[repackage_name],
+            "repackage-signing": upstream_deps[repackage_signing_name],
             "signing": upstream_deps[signing_name],
-            "mar-signing": upstream_deps[mar_signing_name],
         }
         if 'partials-signing' in upstream_deps:
             dependencies['partials-signing'] = upstream_deps['partials-signing']
         if msi_signing_name in upstream_deps:
             dependencies[msi_signing_name] = upstream_deps[msi_signing_name]
-        if repackage_signing_name in upstream_deps:
-            dependencies["repackage-signing"] = upstream_deps[repackage_signing_name]
 
         attributes = copy_attributes_from_dependent_job(dep_job)
-        attributes.update(job.get('attributes', {}))
         if job.get('locale'):
             attributes['locale'] = job['locale']
 
         bucket_scope = get_beetmover_bucket_scope(config)
         action_scope = get_beetmover_action_scope(config)
 
         task = {
             'label': label,
@@ -262,17 +254,16 @@ def make_task_description(config, jobs):
 
 def generate_upstream_artifacts(job, dependencies, platform, locale=None, project=None):
 
     build_mapping = UPSTREAM_ARTIFACT_UNSIGNED_PATHS
     build_signing_mapping = UPSTREAM_ARTIFACT_SIGNED_PATHS
     repackage_mapping = UPSTREAM_ARTIFACT_REPACKAGE_PATHS
     repackage_signing_mapping = UPSTREAM_ARTIFACT_SIGNED_REPACKAGE_PATHS
     msi_signing_mapping = UPSTREAM_ARTIFACT_SIGNED_MSI_PATHS
-    mar_signing_mapping = UPSTREAM_ARTIFACT_SIGNED_MAR_PATHS
 
     artifact_prefix = get_artifact_prefix(job)
     if locale:
         artifact_prefix = '{}/{}'.format(artifact_prefix, locale)
         platform = "{}-l10n".format(platform)
 
     upstream_artifacts = []
 
@@ -306,17 +297,16 @@ def generate_upstream_artifacts(job, dep
                         "paths": ["{}/{}".format(artifact_prefix, path) for path in usable_paths],
                         "locale": locale or "en-US",
                     })
 
     for task_type, cot_type, paths in [
         ('repackage', 'repackage', repackage_mapping),
         ('repackage-signing', 'repackage', repackage_signing_mapping),
         ('repackage-signing-msi', 'repackage', msi_signing_mapping),
-        ('mar-signing', 'signing', mar_signing_mapping),
     ]:
         if task_type not in dependencies:
             continue
 
         paths = ["{}/{}".format(artifact_prefix, path) for path in paths]
         paths = [
             path for path in paths
             if path in dependencies[task_type].release_artifacts]
--- a/taskcluster/taskgraph/transforms/beetmover_repackage_l10n.py
+++ b/taskcluster/taskgraph/transforms/beetmover_repackage_l10n.py
@@ -31,15 +31,14 @@ def make_beetmover_description(config, j
         treeherder = {
             'symbol': join_symbol(group, symbol),
         }
 
         beet_description = {
             'label': job['label'],
             'primary-dependency': dep_job,
             'dependent-tasks': job['dependent-tasks'],
-            'attributes': job['attributes'],
             'treeherder': treeherder,
             'locale': locale,
             'shipping-phase': job['shipping-phase'],
             'shipping-product': job['shipping-product'],
         }
         yield beet_description
--- a/taskcluster/taskgraph/transforms/partials.py
+++ b/taskcluster/taskgraph/transforms/partials.py
@@ -53,40 +53,51 @@ def make_task_description(config, jobs):
 
         treeherder.setdefault('platform',
                               "{}/opt".format(dep_th_platform))
         treeherder.setdefault('kind', 'build')
         treeherder.setdefault('tier', 1)
 
         dependent_kind = str(dep_job.kind)
         dependencies = {dependent_kind: dep_job.label}
+        signing_dependencies = dep_job.dependencies
+        # This is so we get the build task etc in our dependencies to
+        # have better beetmover support.
+        dependencies.update(signing_dependencies)
 
         attributes = copy_attributes_from_dependent_job(dep_job)
         locale = dep_job.attributes.get('locale')
         if locale:
             attributes['locale'] = locale
             treeherder['symbol'] = "p({})".format(locale)
-        attributes['shipping_phase'] = job['shipping-phase']
 
         build_locale = locale or 'en-US'
 
         builds = get_builds(config.params['release_history'], dep_th_platform,
                             build_locale)
 
         # If the list is empty there's no available history for this platform
         # and locale combination, so we can't build any partials.
         if not builds:
             continue
 
-        dep_task_ref = '<{}>'.format(dependent_kind)
+        signing_task = None
+        for dependency in sorted(dependencies.keys()):
+            if 'repackage-signing-l10n' in dependency:
+                signing_task = dependency
+                break
+            if 'repackage-signing' in dependency:
+                signing_task = dependency
+                break
+        signing_task_ref = '<{}>'.format(signing_task)
 
         extra = {'funsize': {'partials': list()}}
         update_number = 1
         artifact_path = "{}{}".format(
-            get_taskcluster_artifact_prefix(dep_job, dep_task_ref, locale=locale),
+            get_taskcluster_artifact_prefix(dep_job, signing_task_ref, locale=locale),
             'target.complete.mar'
         )
         for build in sorted(builds):
             partial_info = {
                 'locale': build_locale,
                 'from_mar': builds[build]['mar_url'],
                 'to_mar': {'task-reference': artifact_path},
                 'platform': get_balrog_platform_name(dep_th_platform),
rename from taskcluster/taskgraph/transforms/mar_signing.py
rename to taskcluster/taskgraph/transforms/partials_signing.py
--- a/taskcluster/taskgraph/transforms/mar_signing.py
+++ b/taskcluster/taskgraph/transforms/partials_signing.py
@@ -1,33 +1,32 @@
 # This Source Code Form is subject to the terms of the Mozilla Public
 # License, v. 2.0. If a copy of the MPL was not distributed with this
 # file, You can obtain one at http://mozilla.org/MPL/2.0/.
 """
-Transform the {partials,mar}-signing task into an actual task description.
+Transform the partials task into an actual task description.
 """
 from __future__ import absolute_import, print_function, unicode_literals
 
 from taskgraph.transforms.base import TransformSequence
-from taskgraph.util.attributes import copy_attributes_from_dependent_job, sorted_unique_list
+from taskgraph.util.attributes import copy_attributes_from_dependent_job
 from taskgraph.util.scriptworker import (
     get_signing_cert_scope_per_platform,
     get_worker_type_for_scope,
 )
 from taskgraph.util.partials import get_balrog_platform_name, get_partials_artifacts
 from taskgraph.util.taskcluster import get_artifact_prefix
-from taskgraph.util.treeherder import join_symbol
 
 import logging
 logger = logging.getLogger(__name__)
 
 transforms = TransformSequence()
 
 
-def generate_partials_artifacts(job, release_history, platform, locale=None):
+def generate_upstream_artifacts(job, release_history, platform, locale=None):
     artifact_prefix = get_artifact_prefix(job)
     if locale:
         artifact_prefix = '{}/{}'.format(artifact_prefix, locale)
     else:
         locale = 'en-US'
 
     artifacts = get_partials_artifacts(release_history, platform, locale)
 
@@ -58,93 +57,65 @@ def generate_partials_artifacts(job, rel
     }
 
     if old_mar_upstream_artifacts["paths"]:
         upstream_artifacts.append(old_mar_upstream_artifacts)
 
     return upstream_artifacts
 
 
-def generate_complete_artifacts(job, platform, locale=None):
-    artifact_prefix = get_artifact_prefix(job)
-    if locale:
-        artifact_prefix = '{}/{}'.format(artifact_prefix, locale)
-
-    upstream_artifacts = [{
-        "taskId": {"task-reference": '<{}>'.format(job.kind)},
-        "taskType": 'build',
-        "paths": [
-            "{}/target.complete.mar".format(artifact_prefix)
-        ],
-        "formats": ["autograph_hash_only_mar384"],
-    }]
-
-    return upstream_artifacts
-
-
 @transforms.add
 def make_task_description(config, jobs):
     for job in jobs:
         dep_job = job['primary-dependency']
-        locale = dep_job.attributes.get('locale')
 
         treeherder = job.get('treeherder', {})
-        treeherder['symbol'] = join_symbol(
-            job.get('treeherder-group', 'ms'),
-            locale or 'N'
-        )
+        treeherder.setdefault('symbol', 'ps(N)')
 
         dep_th_platform = dep_job.task.get('extra', {}).get(
             'treeherder', {}).get('machine', {}).get('platform', '')
-        label = job.get('label', "{}-{}".format(config.kind, dep_job.label))
+        label = job.get('label', "partials-signing-{}".format(dep_job.label))
         dep_th_platform = dep_job.task.get('extra', {}).get(
             'treeherder', {}).get('machine', {}).get('platform', '')
         treeherder.setdefault('platform',
                               "{}/opt".format(dep_th_platform))
         treeherder.setdefault('kind', 'build')
         treeherder.setdefault('tier', 1)
 
         dependent_kind = str(dep_job.kind)
         dependencies = {dependent_kind: dep_job.label}
         signing_dependencies = dep_job.dependencies
         # This is so we get the build task etc in our dependencies to
         # have better beetmover support.
         dependencies.update(signing_dependencies)
 
         attributes = copy_attributes_from_dependent_job(dep_job)
-        attributes['required_signoffs'] = sorted_unique_list(
-            attributes.get('required_signoffs', []),
-            job.pop('required_signoffs')
-        )
-        attributes['shipping_phase'] = job['shipping-phase']
+        locale = dep_job.attributes.get('locale')
         if locale:
             attributes['locale'] = locale
+            treeherder['symbol'] = 'ps({})'.format(locale)
 
         balrog_platform = get_balrog_platform_name(dep_th_platform)
-        if config.kind == 'partials-signing':
-            upstream_artifacts = generate_partials_artifacts(
-                dep_job, config.params['release_history'], balrog_platform, locale)
-        else:
-            upstream_artifacts = generate_complete_artifacts(
-                dep_job, balrog_platform, locale)
+        upstream_artifacts = generate_upstream_artifacts(
+            dep_job, config.params['release_history'], balrog_platform, locale)
 
         build_platform = dep_job.attributes.get('build_platform')
         is_nightly = dep_job.attributes.get('nightly')
         signing_cert_scope = get_signing_cert_scope_per_platform(
             build_platform, is_nightly, config
         )
 
         scopes = [signing_cert_scope, 'project:releng:signing:format:autograph_hash_only_mar384']
         if any("mar" in upstream_details["formats"] for upstream_details in upstream_artifacts):
             scopes.append('project:releng:signing:format:mar')
 
         task = {
             'label': label,
-            'description': "{} {}".format(
-                dep_job.task["metadata"]["description"], job['description-suffix']),
+            'description': "{} Partials".format(
+                dep_job.task["metadata"]["description"]),
             'worker-type': get_worker_type_for_scope(config, signing_cert_scope),
             'worker': {'implementation': 'scriptworker-signing',
                        'upstream-artifacts': upstream_artifacts,
                        'max-run-time': 3600},
             'dependencies': dependencies,
             'attributes': attributes,
             'scopes': scopes,
             'run-on-projects': dep_job.attributes.get('run_on_projects'),
--- a/taskcluster/taskgraph/transforms/per_platform_dummy.py
+++ b/taskcluster/taskgraph/transforms/per_platform_dummy.py
@@ -3,29 +3,28 @@
 # file, You can obtain one at http://mozilla.org/MPL/2.0/.
 """
 Transform the repackage task into an actual task description.
 """
 
 from __future__ import absolute_import, print_function, unicode_literals
 
 from taskgraph.transforms.base import TransformSequence
-from taskgraph.util.attributes import copy_attributes_from_dependent_job
 
 transforms = TransformSequence()
 
 
 @transforms.add
 def one_task_per_product_and_platform(config, jobs):
     unique_products_and_platforms = set()
     for job in jobs:
         dep_task = job["primary-dependency"]
         if 'primary-dependency' in job:
             del job['primary-dependency']
         product = dep_task.attributes.get("shipping_product")
         platform = dep_task.attributes.get("build_platform")
         if (product, platform) not in unique_products_and_platforms:
-            attributes = copy_attributes_from_dependent_job(dep_task)
-            attributes.update(job.get('attributes', {}))
-            job['attributes'] = attributes
+            job.setdefault("attributes", {})
+            job["attributes"]["shipping_product"] = product
+            job["attributes"]["build_platform"] = platform
             job["name"] = "{}-{}".format(product, platform)
             yield job
             unique_products_and_platforms.add((product, platform))
--- a/taskcluster/taskgraph/transforms/release_deps.py
+++ b/taskcluster/taskgraph/transforms/release_deps.py
@@ -19,17 +19,16 @@ def add_dependencies(config, jobs):
     for job in jobs:
         dependencies = {}
         # Add any kind_dependencies_tasks with matching product as dependencies
         product = job.get('shipping-product')
         phase = job.get('shipping-phase')
         if product is None:
             continue
 
-        required_signoffs = set(job.setdefault('attributes', {}).get('required_signoffs', []))
         for dep_task in config.kind_dependencies_tasks:
             # Weed out unwanted tasks.
             # XXX we have run-on-projects which specifies the on-push behavior;
             # we need another attribute that specifies release promotion,
             # possibly which action(s) each task belongs in.
             if product == 'fennec':
                 # Don't ship single locale fennec anymore - Bug 1408083
                 attr = dep_task.attributes.get
@@ -43,15 +42,12 @@ def add_dependencies(config, jobs):
             if dep_task.attributes.get("build_platform") and \
                job.get("attributes", {}).get("build_platform"):
                 if dep_task.attributes["build_platform"] != job["attributes"]["build_platform"]:
                     continue
             # Add matching product tasks to deps
             if dep_task.task.get('shipping-product') == product or \
                     dep_task.attributes.get('shipping_product') == product:
                 dependencies[dep_task.label] = dep_task.label
-                required_signoffs.update(dep_task.attributes.get('required_signoffs', []))
 
         job.setdefault('dependencies', {}).update(dependencies)
-        if required_signoffs:
-            job['attributes']['required_signoffs'] = sorted(required_signoffs)
 
         yield job
--- a/taskcluster/taskgraph/transforms/release_generate_checksums_beetmover.py
+++ b/taskcluster/taskgraph/transforms/release_generate_checksums_beetmover.py
@@ -50,18 +50,16 @@ release_generate_checksums_beetmover_sch
 
     # treeherder is allowed here to override any defaults we use for beetmover.  See
     # taskcluster/taskgraph/transforms/task.py for the schema details, and the
     # below transforms for defaults of various values.
     Optional('treeherder'): task_description_schema['treeherder'],
 
     Optional('shipping-phase'): task_description_schema['shipping-phase'],
     Optional('shipping-product'): task_description_schema['shipping-product'],
-
-    Optional('attributes'): task_description_schema['attributes'],
 })
 
 
 @transforms.add
 def validate(config, jobs):
     for job in jobs:
         label = job.get('primary-dependency', object).__dict__.get('label', '?no-label?')
         validate_schema(
--- a/taskcluster/taskgraph/transforms/release_snap_push.py
+++ b/taskcluster/taskgraph/transforms/release_snap_push.py
@@ -29,17 +29,16 @@ push_snap_description_schema = Schema({
     Required('treeherder'): task_description_schema['treeherder'],
     Required('run-on-projects'): task_description_schema['run-on-projects'],
     Required('worker-type'): optionally_keyed_by('release-level', basestring),
     Required('worker'): object,
     Required('scopes'): optionally_keyed_by('project', [basestring]),
     Required('shipping-phase'): task_description_schema['shipping-phase'],
     Required('shipping-product'): task_description_schema['shipping-product'],
     Optional('extra'): task_description_schema['extra'],
-    Optional('attributes'): task_description_schema['attributes'],
 })
 
 
 @transforms.add
 def validate_jobs_schema_transform(config, jobs):
     for job in jobs:
         label = job.get('label', '?no-label?')
         validate_schema(
--- a/taskcluster/taskgraph/transforms/repackage_signing.py
+++ b/taskcluster/taskgraph/transforms/repackage_signing.py
@@ -31,16 +31,18 @@ repackage_signing_description_schema = s
     Required('depname', default='repackage'): basestring,
     Optional('label'): basestring,
     Optional('treeherder'): task_description_schema['treeherder'],
     Optional('shipping-product'): task_description_schema['shipping-product'],
     Optional('shipping-phase'): task_description_schema['shipping-phase'],
 })
 
 SIGNING_FORMATS = {
+    'target.complete.mar': ["autograph_hash_only_mar384"],
+    'target.bz2.complete.mar': ["mar"],
     "target.installer.exe": ["sha2signcode"],
     "target.stub-installer.exe": ["sha2signcodestub"],
     "target.installer.msi": ["sha2signcode"],
 }
 
 
 @transforms.add
 def validate(config, jobs):
--- a/taskcluster/taskgraph/util/attributes.py
+++ b/taskcluster/taskgraph/util/attributes.py
@@ -31,17 +31,16 @@ RELEASE_PROMOTION_PROJECTS = {
     'try-comm-central',
 } | RELEASE_PROJECTS
 
 _OPTIONAL_ATTRIBUTES = (
     'artifact_prefix',
     'l10n_chunk',
     'locale',
     'nightly',
-    'required_signoffs',
     'signed',
     'shipping_phase',
     'shipping_product',
     'stub-installer',
 )
 
 
 def attrmatch(attributes, **kwargs):
@@ -127,14 +126,8 @@ def copy_attributes_from_dependent_job(d
     }
 
     attributes.update({
         attr: dep_job.attributes[attr]
         for attr in _OPTIONAL_ATTRIBUTES if attr in dep_job.attributes
     })
 
     return attributes
-
-
-def sorted_unique_list(*args):
-    """Join one or more lists, and return a sorted list of unique members"""
-    combined = set().union(*args)
-    return sorted(combined)
--- a/taskcluster/taskgraph/util/verify.py
+++ b/taskcluster/taskgraph/util/verify.py
@@ -176,43 +176,16 @@ def verify_dependency_tiers(task, taskgr
                     continue
                 if tier < tiers[d]:
                     raise Exception(
                         '{} (tier {}) cannot depend on {} (tier {})'
                         .format(task.label, printable_tier(tier),
                                 d, printable_tier(tiers[d])))
 
 
-@verifications.add('full_task_graph')
-def verify_required_signoffs(task, taskgraph, scratch_pad):
-    """
-    Task with required signoffs can't be dependencies of tasks with less
-    required signoffs.
-    """
-    all_required_signoffs = scratch_pad
-    if task is not None:
-        all_required_signoffs[task.label] = set(task.attributes.get('required_signoffs', []))
-    else:
-        def printable_signoff(signoffs):
-            if len(signoffs) == 1:
-                return 'required signoff {}'.format(*signoffs)
-            elif signoffs:
-                return 'required signoffs {}'.format(', '.join(signoffs))
-            else:
-                return 'no required signoffs'
-        for task in taskgraph.tasks.itervalues():
-            required_signoffs = all_required_signoffs[task.label]
-            for d in task.dependencies.itervalues():
-                if required_signoffs < all_required_signoffs[d]:
-                    raise Exception(
-                        '{} ({}) cannot depend on {} ({})'
-                        .format(task.label, printable_signoff(required_signoffs),
-                                d, printable_signoff(all_required_signoffs[d])))
-
-
 @verifications.add('optimized_task_graph')
 def verify_always_optimized(task, taskgraph, scratch_pad):
     """
         This function ensures that always-optimized tasks have been optimized.
     """
     if task is None:
         return
     if task.task.get('workerType') == 'always-optimized':