| 1003 | } |
| 1004 | |
| 1005 | async fn setup_swap_zvol(&self, swap_size: u64) -> Result<()> { |
| 1006 | let swapvol_path = "dstack/swap"; |
| 1007 | let swapvol_device_path = format!("/dev/zvol/{swapvol_path}"); |
| 1008 | |
| 1009 | if Path::new(&swapvol_device_path).exists() { |
| 1010 | cmd! { |
| 1011 | zfs set volmode=none $swapvol_path; |
| 1012 | zfs destroy $swapvol_path; |
| 1013 | } |
| 1014 | .context("Failed to destroy swap zvol")?; |
| 1015 | } |
| 1016 | |
| 1017 | if swap_size == 0 { |
| 1018 | return Ok(()); |
| 1019 | } |
| 1020 | |
| 1021 | info!("Creating swap zvol at {swapvol_device_path} (size {swap_size} bytes)"); |
| 1022 | |
| 1023 | let size_str = swap_size.to_string(); |
| 1024 | cmd! { |
| 1025 | zfs create -V $size_str |
| 1026 | -o compression=zle |
| 1027 | -o logbias=throughput |
| 1028 | -o sync=always |
| 1029 | -o primarycache=metadata |
| 1030 | -o com.sun:auto-snapshot=false |
| 1031 | $swapvol_path |
| 1032 | } |
| 1033 | .with_context(|| format!("Failed to create swap zvol {swapvol_path}"))?; |
| 1034 | |
| 1035 | let mut count = 0u32; |
| 1036 | while !Path::new(&swapvol_device_path).exists() && count < 10 { |
| 1037 | std::thread::sleep(Duration::from_secs(1)); |
| 1038 | count += 1; |
| 1039 | } |
| 1040 | if !Path::new(&swapvol_device_path).exists() { |
| 1041 | bail!("Device {swapvol_device_path} did not appear after 10 seconds"); |
| 1042 | } |
| 1043 | |
| 1044 | cmd! { |
| 1045 | mkswap $swapvol_device_path; |
| 1046 | swapon $swapvol_device_path; |
| 1047 | swapon --show; |
| 1048 | } |
| 1049 | .context("Failed to enable swap on zvol")?; |
| 1050 | |
| 1051 | Ok(()) |
| 1052 | } |
| 1053 | |
| 1054 | fn is_disk_initialized(&self, opts: &DstackOptions) -> bool { |
| 1055 | let device = &self.args.device; |