# HG changeset patch # User Thomas Gazagnaire # Date 1268390593 0 # Node ID a1326fcc45c1007189224246c2fc2da6c1573f44 # Parent 020b9a3ea742bd66a0b00ea5549e49eb8c07b4e9 CA-38136: remove the VM.create_template call which duplicates what VM.clone and VM.copy should have done; Extend VM.clone et VM.copy to hard-shutdown the resulting VM if the source VM was a snapshot/checkpoint (ie. throw away the memory image). Signed-off-by: Thomas Gazagnaire diff -r 020b9a3ea742 -r a1326fcc45c1 ocaml/client_records/record_util.ml --- a/ocaml/client_records/record_util.ml Thu Mar 11 13:56:42 2010 +0000 +++ b/ocaml/client_records/record_util.ml Fri Mar 12 10:43:13 2010 +0000 @@ -35,7 +35,6 @@ `clean_reboot, "clean_reboot"; `clean_shutdown, "clean_shutdown"; `clone, "clone"; - `create_template, "create_template"; `snapshot, "snapshot"; `checkpoint, "checkpoint"; `snapshot_with_quiesce, "snapshot_with_quiesce"; diff -r 020b9a3ea742 -r a1326fcc45c1 ocaml/idl/datamodel.ml --- a/ocaml/idl/datamodel.ml Thu Mar 11 13:56:42 2010 +0000 +++ b/ocaml/idl/datamodel.ml Fri Mar 12 10:43:13 2010 +0000 @@ -1258,19 +1258,6 @@ ~errs:[Api_errors.vm_bad_power_state; Api_errors.sr_full; Api_errors.operation_not_allowed; Api_errors.vm_checkpoint_suspend_failed; Api_errors.vm_checkpoint_resume_failed] ~allowed_roles:_R_VM_POWER_ADMIN - () - -let vm_create_template = call - ~name:"create_template" - ~in_product_since:rel_midnight_ride - ~doc:"Creates a new template by cloning the specified VM. Clone automatically exploits the capabilities of the underlying storage repository in which the VM's disk images are stored (e.g. Copy on Write)." - ~result:(Ref _vm, "The reference of the newly created template.") - ~params:[ - Ref _vm, "vm", "The VM to be cloned"; - String, "new_name", "The name of the new template" - ] - ~errs:[Api_errors.vm_bad_power_state; Api_errors.sr_full; Api_errors.operation_not_allowed] - ~allowed_roles:_R_VM_ADMIN () (* VM.Provision -- causes the template's disks to be instantiated *) @@ -5406,7 +5393,7 @@ let vm_operations = Enum ("vm_operations", List.map operation_enum - [ vm_snapshot; vm_clone; vm_copy; vm_create_template; vm_revert; vm_checkpoint; vm_snapshot_with_quiesce; + [ vm_snapshot; vm_clone; vm_copy; vm_revert; vm_checkpoint; vm_snapshot_with_quiesce; vm_provision; vm_start; vm_start_on; vm_pause; vm_unpause; vm_cleanShutdown; vm_cleanReboot; vm_hardShutdown; vm_stateReset; vm_hardReboot; vm_suspend; csvm; vm_resume; vm_resume_on; @@ -5440,7 +5427,7 @@ ~gen_events:true ~doccomments:[ "destroy", "Destroy the specified VM. The VM is completely removed from the system. This function can only be called when the VM is in the Halted State." ] ~messages_default_allowed_roles:_R_VM_ADMIN - ~messages:[ vm_snapshot; vm_snapshot_with_quiesce; vm_clone; vm_copy; vm_create_template; vm_revert; vm_checkpoint; + ~messages:[ vm_snapshot; vm_snapshot_with_quiesce; vm_clone; vm_copy; vm_revert; vm_checkpoint; vm_provision; vm_start; vm_start_on; vm_pause; vm_unpause; vm_cleanShutdown; vm_cleanReboot; vm_hardShutdown; vm_stateReset; vm_hardReboot; vm_suspend; csvm; vm_resume; vm_hardReboot_internal; diff -r 020b9a3ea742 -r a1326fcc45c1 ocaml/xapi/cli_operations.ml --- a/ocaml/xapi/cli_operations.ml Thu Mar 11 13:56:42 2010 +0000 +++ b/ocaml/xapi/cli_operations.ml Fri Mar 12 10:43:13 2010 +0000 @@ -2008,9 +2008,7 @@ (* We should now have an sr-uuid *) let new_vm = - if Client.VM.get_is_a_snapshot rpc session_id template - then Client.VM.create_template rpc session_id template name - else if List.mem_assoc "sr-name-label" params || List.mem_assoc "sr-uuid" params + if List.mem_assoc "sr-name-label" params || List.mem_assoc "sr-uuid" params then Client.VM.copy rpc session_id template name (Client.SR.get_by_uuid rpc session_id sr_uuid) else Client.VM.clone rpc session_id template name in @@ -2184,7 +2182,7 @@ let new_uuid = Client.VM.get_uuid ~rpc ~session_id ~self:new_ref in printer (Cli_printer.PList [new_uuid]) -let snapshot_create_template printer = snapshot_op Client.VM.create_template printer +let snapshot_create_template printer = snapshot_op Client.VM.clone printer let snapshot_destroy printer rpc session_id params = let snap_uuid = List.assoc "snapshot-uuid" params in diff -r 020b9a3ea742 -r a1326fcc45c1 ocaml/xapi/message_forwarding.ml --- a/ocaml/xapi/message_forwarding.ml Thu Mar 11 13:56:42 2010 +0000 +++ b/ocaml/xapi/message_forwarding.ml Fri Mar 12 10:43:13 2010 +0000 @@ -879,11 +879,6 @@ (fun () -> forward_to_access_srs ~local_fn ~__context ~vm (fun session_id rpc -> Client.VM.clone rpc session_id vm new_name)) - - let create_template ~__context ~vm ~new_name = - info "VM.create_template: VM = '%s'; new_name = '%s'" (vm_uuid ~__context vm) new_name; - with_vm_operation ~__context ~self:vm ~doc:"VM.create_template" ~op:`create_template - (fun () -> Local.VM.create_template ~__context ~vm ~new_name) let update_snapshot_metadata ~__context ~vm ~snapshot_of ~snapshot_time ~transportable_snapshot_id = Db.VM.set_is_a_snapshot ~__context ~self:vm ~value:true; diff -r 020b9a3ea742 -r a1326fcc45c1 ocaml/xapi/xapi_vm.ml --- a/ocaml/xapi/xapi_vm.ml Thu Mar 11 13:56:42 2010 +0000 +++ b/ocaml/xapi/xapi_vm.ml Fri Mar 12 10:43:13 2010 +0000 @@ -942,7 +942,10 @@ (* Now that clones are "fast", there's no need to put this operation in the "normal_vm_queue". Indeed, putting it in there would mean that clones are serialized on a host-basis whereas they may be able to proceed in parallel. *) - Xapi_vm_clone.clone Xapi_vm_clone.Disk_op_clone ~__context ~vm ~new_name + let new_vm = Xapi_vm_clone.clone Xapi_vm_clone.Disk_op_clone ~__context ~vm ~new_name in + if Db.VM.get_is_a_snapshot ~__context ~self:vm && Db.VM.get_power_state ~__context ~self:new_vm <> `Halted then + hard_shutdown ~__context ~vm:new_vm; + new_vm (* We do call wait_in_line for snapshot and snapshot_with_quiesce because the locks are taken at *) (* the VBD level (with pause/unpause mechanism *) @@ -955,12 +958,6 @@ let snapshot_with_quiesce ~__context ~vm ~new_name = TaskHelper.set_cancellable ~__context; Xapi_vm_snapshot.snapshot_with_quiesce ~__context ~vm ~new_name - -let create_template ~__context ~vm ~new_name = - let new_vm = clone ~__context ~vm ~new_name in - if Db.VM.get_power_state ~__context ~self:new_vm <> `Halted then - hard_shutdown ~__context ~vm:new_vm; - new_vm (* As we will destroy the domain ourself, we grab the vm_lock here in order to tell the event thread to *) (* do not look at this domain. The message forwarding layer already checked that the VM reference we *) @@ -1001,7 +998,10 @@ Local_work_queue.wait_in_line Local_work_queue.long_running_queue (Printf.sprintf "VM.copy %s" (Context.string_of_task __context)) (fun () -> - Xapi_vm_clone.clone (Xapi_vm_clone.Disk_op_copy sr) ~__context ~vm ~new_name + let new_vm = Xapi_vm_clone.clone (Xapi_vm_clone.Disk_op_copy sr) ~__context ~vm ~new_name in + if Db.VM.get_is_a_snapshot ~__context ~self:vm && Db.VM.get_power_state ~__context ~self:new_vm <> `Halted then + hard_shutdown ~__context ~vm:new_vm; + new_vm ) let provision ~__context ~vm = diff -r 020b9a3ea742 -r a1326fcc45c1 ocaml/xapi/xapi_vm.mli --- a/ocaml/xapi/xapi_vm.mli Thu Mar 11 13:56:42 2010 +0000 +++ b/ocaml/xapi/xapi_vm.mli Fri Mar 12 10:43:13 2010 +0000 @@ -191,8 +191,6 @@ __context:Context.t -> vm:API.ref_VM -> new_name:string -> [ `VM ] Ref.t val snapshot_with_quiesce : __context:Context.t -> vm:[ `VM ] Ref.t -> new_name:string -> [ `VM ] Ref.t -val create_template : - __context:Context.t -> vm:API.ref_VM -> new_name:string -> [ `VM ] Ref.t val revert : __context:Context.t -> snapshot:[ `VM ] Ref.t -> unit val checkpoint : __context:Context.t -> vm:API.ref_VM -> new_name:string -> [ `VM ] Ref.t diff -r 020b9a3ea742 -r a1326fcc45c1 ocaml/xapi/xapi_vm_lifecycle.ml --- a/ocaml/xapi/xapi_vm_lifecycle.ml Thu Mar 11 13:56:42 2010 +0000 +++ b/ocaml/xapi/xapi_vm_lifecycle.ml Fri Mar 12 10:43:13 2010 +0000 @@ -64,7 +64,6 @@ -> [`Halted; `Running] | `clone | `copy - | `create_template | `export -> [`Halted; `Suspended] | `hard_reboot @@ -91,7 +90,7 @@ Remark: we do not test whether the power-state is valid. *) let is_allowed_concurrently ~(op:API.vm_operations) ~current_ops = (* declare below the non-conflicting concurrent sets. *) - let long_copies = [`clone; `copy; `export; `create_template] + let long_copies = [`clone; `copy; `export ] and boot_record = [`get_boot_record] and snapshot = [`snapshot; `checkpoint] and allowed_operations = (* a list of valid state -> operation *) @@ -168,7 +167,6 @@ `changing_memory_limits; `clone; `copy; - `create_template; `export; `metadata_export; `provision; @@ -180,7 +178,7 @@ else Some (Api_errors.vm_is_template, [ref_str; Record_util.vm_operation_to_string op]) let check_snapshot ~vmr ~op ~ref_str = - let allowed = [`revert; `create_template; `export; `destroy; `hard_shutdown; `metadata_export] in + let allowed = [`revert; `clone; `copy; `export; `destroy; `hard_shutdown; `metadata_export] in if List.mem op allowed then None else Some (Api_errors.vm_is_snapshot, [ref_str; Record_util.vm_operation_to_string op]) @@ -295,7 +293,7 @@ in let allowed = List.fold_left check [] - [`snapshot; `copy; `clone; `create_template; `revert; `checkpoint; `snapshot_with_quiesce; + [`snapshot; `copy; `clone; `revert; `checkpoint; `snapshot_with_quiesce; `start; `start_on; `pause; `unpause; `clean_shutdown; `clean_reboot; `hard_shutdown; `hard_reboot; `suspend; `resume; `resume_on; `export; `destroy; `provision; `changing_VCPUs_live; `pool_migrate; `make_into_template; `changing_static_range;