Q: PDM LXC migration drama moving container from Prox9<>Prox8 sanity checking

fortechitsolutions

Renowned Member
Jun 4, 2008
488
66
93
Hi everyone, just a quick sanity check question. I've been meaning to do some PDM testing and finally got my kick yesterday to get on with it.
after first bit of testing I must say, 'very nice' - this looks like a great tool to enhance management options for more complex setup
when a simple 'single pane of glass for a single cluster' is not sufficient (ie, multi cluter / mutli standalone proxmox management).
So - very nice.

I seem to have bumped an issue yesterday and wanted to confirm if this is a known issue

context / use case here for me. Possibly this alone will make you go 'ah, arrgh' and explain maybe the drama. (I don't know)

I'm mostly done now, with a little adventure

Upgrade on a modest sized proxmox cluster that was running proxmox.v8 / and it is a mix of similar-but-not-identical hardware nodes
they all have been installed 'gradually, over the years' growth. Cluster started as one node a bunch of years ago. Then was scaled to a 3-node cluster, Upgraded to new proxmox version in place. More incremental growth / addition of nodes / more in-place version upgrades of proxmox versions as the years marched by. Still chugging.

Drama is that being a stack with some history, there are some old containers. I had lost track of the looming drama, with upgrade from Proxmox v8 to v9 that cgroup version changes meant life was going to be a bit interesting yesterday. Sigh. (ie, old containers don't start well / network is borked / cannot work / etc)

So my clever plan, was to light up a new hardware node, running proxmox v9
run a nested proxmoxv8 inside of this, because the new node is snappy enough (NVME raid, etc vs older sata rust disk raid) that despite being slightly insane
it gives me a place to move the old VM workload until I can help client move along with container upgrades to not-ancient OS guests.
since proxmoxv8 is purely internally accessible, not attached to public internets etc in any way this lunacy seems like a decent work around
plus all the guest workload here is lxc containers basically, and from what I've seen majority of proxmox nested performance drama might arise when doing KVM VM guests on the inner most layer of this inception-like game.

So far so good with the guests working in this nested place.

So, anyhow. enough story telling. The drama appears to arise Thus.

My clever plan was to use PDM as a convenient way to move LXC Containers from the old bad place (ie, V8>V9 upgraded proxmox, where they no longer work)
over to the nested V8Proxmox where they can run happily.

What appears to happen? with this cross-proxmox-version LXC Container move
is that everything goes perfectly. except for one snag, which I am guessing maybe is due to PDM trying to be clever, or making assumptions about config file formatting, or how the config is 'copied' or 'migrated' or something like that, in my ?edge case? where PDM is talking to different version of Proxmox on the send-vs-recieve side of the migration (?)

anyhoo. short and long is that - once I move an LXC Container over
there is an unwanted line appended to the end of the LXC Config, simply reads

Code:
unprivileged:

and this makes the LXC container start with an error if I do not catch it - but it does start - but causes some concern (* and - behaviour inside the vm is awful, due to it being not clear if this is PRIV vs UNPRIV container. So basically it is unusable actually]. The fix it seems is just to manually copy over the CONF file from old to new proxmox, or to manually edit the CONF File post-migration to ensure the unwanted line is gone / that the conf file is 'same after migration as it was before migration'. That process is slightly harder to do with confidence if you have already done a 'delete when done' migration. :-) but not impossible of course if you have good backups parked somewhereon a PBS box, so trivial to 'go take a look and confirm what the CONF file used to look like'.

I've found as a reference/sanity check. If I do LXC "Migrations" via PBS method (ie, I have my old proxmox host running ProxV9 linked to a PBS server and now also my new nested ProxV8 host also linked to same PBS server). Doing a restore of an LXC Container from that PBS into the new-nested place. Things go 'perfect' as one might expect

otherwise the only side-note observation, (Side topic!) is that the PDM based lxc migration seems to use 'vzmtunnel' (API based presumably) method to push data vs PBS restores - is doing something bit different - and I wonder if the vzmt method is not-sparse-aware maybe (ie, seems to have longer copy times for similar containers?) but I could be entirely mistaken (ie, my containers are different sizes and I have trouble keeping track of what is what)

anyhow. ultimately this very long winded post was just an attempt to

- give context on this use case
- observation about odd behaviour in this setup, for lxc container <> config file small drama <> sanity check if anyone else has ever seen or if this is a bug-glitch in PDM
- and other general story time thoughts.

hope if you read this far it is not too much regretted. :-)
Thanks
Tim
 
Last edited:
Footnote, side quest observation part2. It looks like in my setup, once a PDM managed LXC migration happens. The SRC and TARGET nodes leave the lxc containers tagged in a lock state of "Migrate" and I need to manualy unlock them via CLI. Which is not a big deal. But another hint maybe that something is not happy about this use case / PDM is grumpy somehow / and despite in the PDM GUI it claims the migrate is done. And on the Proxmox node we see the "JOB/TASK" claims it is 'done'. this loose end remains.
 
Footnote, side quest observation part2. It looks like in my setup, once a PDM managed LXC migration happens. The SRC and TARGET nodes leave the lxc containers tagged in a lock state of "Migrate" and I need to manualy unlock them via CLI. Which is not a big deal. But another hint maybe that something is not happy about this use case / PDM is grumpy somehow / and despite in the PDM GUI it claims the migrate is done. And on the Proxmox node we see the "JOB/TASK" claims it is 'done'. this loose end remains.

this is normal - if you do not delete the source as part of the migration, it will be left in a locked state to prevent accidental starts (it's usually not desired to have two identical instances of the same guest running in two places).

regarding your original issue, could you please provide:
- pveversion -v from both sides
- the full config file of the source container before migration
- the full config file of the target container after migration (before you clean anything up)
- the migration task log

thanks!
 
  • Like
Reactions: Johannes S
Hi Fabian, thank you for this reply. Greatly appreciated. This makes sense that the VM are left locked on Source/Target. I think here I just have a learning curve about how PDM works. So that is good!

In terms of the original issue, and some followup detail, here is reply/infos:

- pveversion -v from both sides
- the full config file of the source container before migration
- the full config file of the target container after migration (before you clean anything up)
- the migration task log

Code:
PVE Versions Info
Source Side
==================

proxmox-ve: 9.2.0 (running kernel: 7.0.14-15-pve)
pve-manager: 9.2.11 (running version: 9.2.11/f6997e698c7933ea)
proxmox-kernel-helper: 9.2.0
proxmox-kernel-7.0: 7.0.14-15
proxmox-kernel-7.0.14-15-pve-signed: 7.0.14-15
ceph-fuse: 19.2.3-pve1
corosync: 3.1.10-pve3
criu: 4.1.1-1
frr-pythontools: 10.6.1-1+pve3
ifupdown: residual config
ifupdown2: 3.3.0-1+pmx12
intel-microcode: 3.20251111.1~deb13u1
ksm-control-daemon: 1.5-1
libjs-extjs: 7.0.0-7
libproxmox-acme-perl: 1.7.2
libproxmox-backup-qemu0: 2.0.2
libproxmox-rs-perl: 0.4.1
libpve-access-control: 9.1.1
libpve-apiclient-perl: 3.4.3
libpve-cluster-api-perl: 9.1.6
libpve-cluster-perl: 9.1.6
libpve-common-perl: 9.2.1
libpve-guest-common-perl: 6.0.5
libpve-http-server-perl: 6.0.5
libpve-network-perl: 1.6.7
libpve-notify-perl: 9.1.6
libpve-rs-perl: 0.15.3
libpve-storage-perl: 9.1.10
libspice-server1: 0.15.2-1+b1
lvm2: 2.03.31-2+pmx1
lxc-pve: 7.0.0-2
lxcfs: 7.0.0-pve1
novnc-pve: 1.7.0-2
proxmox-backup-client: 4.2.5-1
proxmox-backup-file-restore: 4.2.5-1
proxmox-backup-restore-image: 1.0.0
proxmox-enterprise-support-keyring: 1.1
proxmox-firewall: 1.2.3
proxmox-kernel-helper: 9.2.0
proxmox-mail-forward: 1.0.3
proxmox-mini-journalreader: 1.7
proxmox-offline-mirror-helper: 0.7.4
proxmox-widget-toolkit: 5.2.8
pve-cluster: 9.1.6
pve-container: 6.1.14
pve-docs: 9.2.4
pve-edk2-firmware: not correctly installed
pve-esxi-import-tools: 1.0.1
pve-firewall: 6.0.5
pve-firmware: 3.18-6
pve-ha-manager: 5.2.5
pve-i18n: 3.10.0
pve-qemu-kvm: 11.0.3-3
pve-xtermjs: 6.0.0-2
qemu-server: 9.2.7
smartmontools: 7.5-pve2
spiceterm: 3.4.2
swtpm: 0.8.0+pve3
vncterm: 1.9.2
zfsutils-linux: 2.4.4-pve1
root@SOURCE:~#


TARGET SIDE
===========================
proxmox-ve: 8.4.0 (running kernel: 6.8.12-43-pve)
pve-manager: 8.4.21 (running version: 8.4.21/2606ac850d46da29)
proxmox-kernel-helper: 8.1.4
proxmox-kernel-6.8.12-43-pve-signed: 6.8.12-43
proxmox-kernel-6.8: 6.8.12-43
ceph-fuse: 16.2.15+ds-0+deb12u2
corosync: 3.1.10-pve2~bpo12+1
criu: 3.17.1-2+deb12u2
glusterfs-client: 10.3-5
ifupdown: residual config
ifupdown2: 3.2.0-1+pmx11
intel-microcode: 3.20251111.1~deb12u1
libjs-extjs: 7.0.0-7
libknet1: 1.30-pve2
libproxmox-acme-perl: 1.6.0
libproxmox-backup-qemu0: 1.5.2
libproxmox-rs-perl: 0.3.5
libpve-access-control: 8.2.3
libpve-apiclient-perl: 3.3.2
libpve-cluster-api-perl: 8.1.3
libpve-cluster-perl: 8.1.3
libpve-common-perl: 8.3.8
libpve-guest-common-perl: 5.2.2
libpve-http-server-perl: 5.2.2
libpve-network-perl: 0.11.3
libpve-rs-perl: 0.9.4
libpve-storage-perl: 8.3.8
libspice-server1: 0.15.1-1
lvm2: 2.03.16-2
lxc-pve: 6.0.0-2
lxcfs: 6.0.0-pve2
novnc-pve: 1.6.0-2.1
proxmox-backup-client: 3.4.9-1
proxmox-backup-file-restore: 3.4.9-1
proxmox-backup-restore-image: 0.7.0
proxmox-firewall: 0.7.1
proxmox-kernel-helper: 8.1.4
proxmox-mail-forward: 0.3.3
proxmox-mini-journalreader: 1.5
proxmox-offline-mirror-helper: 0.6.8
proxmox-widget-toolkit: 4.3.18
pve-cluster: 8.1.3
pve-container: 5.3.6
pve-docs: 8.4.2
pve-edk2-firmware: not correctly installed
pve-esxi-import-tools: 0.7.4
pve-firewall: 5.1.3
pve-firmware: 3.16-3
pve-ha-manager: 4.0.7
pve-i18n: 3.4.5
pve-qemu-kvm: 9.2.0-8
pve-xtermjs: 5.5.0-2
qemu-server: 8.4.10
smartmontools: 7.3-pve1
spiceterm: 3.3.1
swtpm: 0.8.0+pve1
vncterm: 1.8.2
zfsutils-linux: 2.2.10-pve1
root@TARGET-nested:~#


SAMPLE CONTAINER CONFIG

FROM SOURCE SIDE (SLIGHT SANITIZED)
===================================
#192.168.95.6%09CACTI
#Debian9 LXC template
#stock cacti VM for monitoring
#
#32gig VM Disk local storage, 1 cpu, 1gig ram - nothing fancy.
arch: amd64
cores: 1
hostname: cacti
memory: 1024
net0: name=eth0,bridge=vmbr1,gw=192.168.95.1,hwaddr=X6:XC:X3:XA:XA:X7,ip=192.168.95.X/32,type=veth
onboot: 1
ostype: debian
rootfs: local:104/vm-104-disk-1.raw,size=32G
swap: 0


TARGET SIDE ALSO SAME SANITIZED after PDM Migration happened

#192.168.95.6%09CACTI
#Debian9 LXC template
#stock cacti VM for monitoring
#
#32gig VM Disk local storage, 1 cpu, 1gig ram - nothing fancy.
arch: amd64
cores: 1
hostname: cacti
memory: 1024
net0: name=eth0,bridge=vmbr1,gw=192.168.95.1,hwaddr=X6:XC:X3:XA:XA:X7,ip=192.168.95.X/32,type=veth
onboot: 1
ostype: debian
rootfs: local:104/vm-104-disk-1.raw,size=32G
swap: 0
unprivileged:


MIGRATION TASK LOG
====================

Task Viewer: CT 104 - Migrate
2026-09-07 08:02:31 remote: started tunnel worker 'UPID:nested:00055DD2:00500748:6A9E99C7:vzmtunnel:104:root@pam!pdm-admin-cluster-manager:'
tunnel: -> sending command "version" to remote
tunnel: <- got reply
2026-09-07 08:02:31 local WS tunnel version: 2
2026-09-07 08:02:31 remote WS tunnel version: 2
2026-09-07 08:02:31 minimum required WS tunnel version: 2
2026-09-07 08:02:31 websocket tunnel started
2026-09-07 08:02:31 starting migration of CT 104 to node 'nested' (nested)
tunnel: -> sending command "bwlimit" to remote
tunnel: <- got reply
2026-09-07 08:02:31 found local volume 'local:104/vm-104-disk-1.raw' (in current VM config)
tunnel: -> sending command "disk-import" to remote
tunnel: <- got reply
tunnel: accepted new connection on '/run/pve/104.storage'
tunnel: requesting WS ticket via tunnel
tunnel: established new WS for forwarding '/run/pve/104.storage'

32116736 bytes (32 MB, 31 MiB) copied, 1 s, 31.9 MB/s
62296064 bytes (62 MB, 59 MiB) copied, 2 s, 31.1 MB/s
93048832 bytes (93 MB, 89 MiB) copied, 3 s, 31.0 MB/s.....
TRIMMED........... many lines .. All similar just speeds and zooming along....
34268860416 bytes (34 GB, 32 GiB) copied, 1116 s, 30.7 MB/s
34299891712 bytes (34 GB, 32 GiB) copied, 1117 s, 30.7 MB/s
34330710016 bytes (34 GB, 32 GiB) copied, 1118 s, 30.7 MB/s
8388608+0 records in
8388608+0 records out
34359738368 bytes (34 GB, 32 GiB) copied, 1118.94 s, 30.7 MB/s
tunnel: -> sending command "query-disk-import" to remote
tunnel: done handling forwarded connection from '/run/pve/104.storage'
tunnel: <- got reply
2026-09-07 08:21:12 disk-import: Formatting '/var/lib/vz/images/104/vm-104-disk-1.raw', fmt=raw size=34359738368 preallocation=off
tunnel: -> sending command "query-disk-import" to remote
tunnel: <- got reply
2026-09-07 08:21:13 disk-import: 208+2096010 records in
tunnel: -> sending command "query-disk-import" to remote
tunnel: <- got reply
2026-09-07 08:21:14 disk-import: 208+2096010 records out
tunnel: -> sending command "query-disk-import" to remote
tunnel: <- got reply
2026-09-07 08:21:15 disk-import: 34359738368 bytes (34 GB, 32 GiB) copied, 1118.95 s, 30.7 MB/s
tunnel: -> sending command "query-disk-import" to remote
tunnel: <- got reply
2026-09-07 08:21:16 volume 'local:104/vm-104-disk-1.raw' is 'local:104/vm-104-disk-1.raw' on the target
2026-09-07 08:21:16 mapped: net0 from vmbr1 to vmbr1
tunnel: -> sending command "config" to remote
tunnel: <- got reply
2026-09-07 08:21:16 start final cleanup
tunnel: -> sending command "unlock" to remote
tunnel: <- got reply
tunnel: -> sending command "quit" to remote
tunnel: <- got reply
2026-09-07 08:21:17 migration finished successfully (duration 00:18:46)
TASK OK

I think that is about it.

I just had small bit of added fun thisAM, post upgrade yesterday I had to fuddle about with some self-signed-ssl-cert-regeneration in my cluster - not quite certain why - VNC console was complaining, then had to redo self-sign-certs across the board it seems - to shush up that sadness - then PDM was grumpy my cluster certs all were not what it expected - just fixed that up - then things appear all happy, talking again. And harvest info was ok-easy-doable. this is just side quest footnote.

I hope this detail gives a tiny bit of help
and that I got the proper things / to the right amount of detail

thank you,

Tim
 
I see the issue. it also affects the other direction with your particular config as far as I can tell. given that PVE 8.x is EOL, it won't be fixed there. but explicitly marking your containers as privileged on the source side before attempting the migration should do the trick (by adding an unprivileged: 0 line).

note: I'd really recommend switching your workloads to unprivileged containers - there's a reason that is the default on creation nowadays!
 
Hi, OK. Thank you for confirming. I think the distinction between "Unpriv: NO" setting in the GUI (ie, this is how it is now) vs trying to flag it as "PRIV: YES" is maybe not entirely clear. But bigger picture, I agree, these are old containers / setup and deployed >more years ago than seems possible now
and definitely by default I am doing unprivileged as baseline default always now. So. Ultimately. This is not a 'big deal'.

Again in this context, the migration of containers back to Proxmox.V8.EOL was purely to accommodate legacy workload cgroup constraint drama.
Once I figured out that "ah the migration is ok, the config file is just slightly screwed up" - it was less anxiety provoking. But it was just slightly disorienting initially to migrate VM with PDM > have it "work" and then the config file getting mulched slightly / having the VM behave badly. Until I figured out, 'wait I can just edit this config file by hand, it is fine, this is not a big deal".

I will be working with my client in this context to get all the legacy stuff retired, which will take care of the unwanted old platform LXC Containers; get things onto newer/current LXC/debian guest versions; and deal with unprivileged vs privileged situation. Always fun supporting a long-running platform.

Thank you for looking at this / and confirming the detail around this.

Tim