docs: def save_gmfs(calculator):
      """
      :param calculator: a scenario_risk/damage or event_based_risk calculator
      :returns: a pair (eids, R) where R is the number of realizations
      """
      dstore = calculator.datastore
      oq = calculator.oqparam
      logging.info('Reading gmfs from file')
      if oq.inputs['gmfs'].endswith('.csv'):
          # TODO: check if import_gmfs can be removed
          eids = import_gmfs(
              dstore, oq.inputs['gmfs'], calculator.sitecol.complete.sids)
      else:  # XML
          eids, gmfs = readinput.eids, readinput.gmfs
      E = len(eids)
      events = numpy.zeros(E, rupture.events_dt)
      events['eid'] = eids
      calculator.eids = eids
      if hasattr(oq, 'number_of_ground_motion_fields'):
          if oq.number_of_ground_motion_fields != E:
              raise RuntimeError(
                  'Expected %d ground motion fields, found %d' %
                  (oq.number_of_ground_motion_fields, E))
      else:  # set the number of GMFs from the file
          oq.number_of_ground_motion_fields = E
      # NB: save_gmfs redefine oq.sites in case of GMFs from XML or CSV
      if oq.inputs['gmfs'].endswith('.xml'):
          haz_sitecol = readinput.get_site_collection(oq)
          N, E, M = gmfs.shape
          save_gmf_data(dstore, haz_sitecol, gmfs[haz_sitecol.sids],
                        oq.imtls, events)