1.\" Copyright (c) 2013-2018 Devin Teske 2.\" All rights reserved. 3.\" 4.\" Redistribution and use in source and binary forms, with or without 5.\" modification, are permitted provided that the following conditions 6.\" are met: 7.\" 1. Redistributions of source code must retain the above copyright 8.\" notice, this list of conditions and the following disclaimer. 9.\" 2. Redistributions in binary form must reproduce the above copyright 10.\" notice, this list of conditions and the following disclaimer in the 11.\" documentation and/or other materials provided with the distribution. 12.\" 13.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 14.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 15.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 16.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 17.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 18.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 19.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 20.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 21.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 22.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 23.\" SUCH DAMAGE. 24.\" 25.Dd March 13, 2018 26.Dt DPV 3 27.Os 28.Sh NAME 29.Nm dpv 30.Nd dialog progress view library 31.Sh LIBRARY 32.Lb libdpv 33.Sh SYNOPSIS 34.In dpv.h 35.Ft int 36.Fo dpv 37.Fa "struct dpv_config *config" 38.Fa "struct dpv_file_node *file_list" 39.Fc 40.Ft void 41.Fo dpv_free 42.Fa "void" 43.Fc 44.Sh DESCRIPTION 45The 46.Nm 47library provides an interface for creating complex 48.Dq gauge 49widgets for displaying progress on various actions. 50The 51.Nm 52library can display progress with one of 53.Xr dialog 3 , 54.Xr dialog 1 , 55or 56.Xr Xdialog 1 Pq Pa ports/x11/xdialog . 57.Pp 58The 59.Fn dpv 60.Fa config 61argument properties for configuring global display features: 62.Bd -literal -offset indent 63struct dpv_config { 64 uint8_t keep_tite; /* Cleaner exit for scripts */ 65 enum dpv_display display_type; /* Def. DPV_DISPLAY_LIBDIALOG */ 66 enum dpv_output output_type; /* Default DPV_OUTPUT_NONE */ 67 int debug; /* Enable debug on stderr */ 68 int display_limit; /* Files/page. Default -1 */ 69 int label_size; /* Label size. Default 28 */ 70 int pbar_size; /* Mini-progress size */ 71 int dialog_updates_per_second; /* Default 16 */ 72 int status_updates_per_second; /* Default 2 */ 73 uint16_t options; /* Default 0 (none) */ 74 char *title; /* Widget title */ 75 char *backtitle; /* Widget backtitle */ 76 char *aprompt; /* Append. Default NULL */ 77 char *pprompt; /* Prefix. Default NULL */ 78 char *msg_done; /* Default `Done' */ 79 char *msg_fail; /* Default `Fail' */ 80 char *msg_pending; /* Default `Pending' */ 81 char *output; /* Output format string */ 82 const char *status_solo; /* dialog(3) solo-status format. 83 * Default DPV_STATUS_SOLO */ 84 const char *status_many; /* dialog(3) many-status format. 85 * Default DPV_STATUS_MANY */ 86 87 /* 88 * Function pointer; action to perform data transfer 89 */ 90 int (*action)(struct dpv_file_node *file, int out); 91}; 92 93enum dpv_display { 94 DPV_DISPLAY_LIBDIALOG = 0, /* Use dialog(3) (default) */ 95 DPV_DISPLAY_STDOUT, /* Use stdout */ 96 DPV_DISPLAY_DIALOG, /* Use spawned dialog(1) */ 97 DPV_DISPLAY_XDIALOG, /* Use spawned Xdialog(1) */ 98}; 99 100enum dpv_output { 101 DPV_OUTPUT_NONE = 0, /* No output (default) */ 102 DPV_OUTPUT_FILE, /* Read `output' member as file path */ 103 DPV_OUTPUT_SHELL, /* Read `output' member as shell cmd */ 104}; 105.Ed 106.Pp 107The 108.Va options 109member of the 110.Fn dpv 111.Fa config 112argument is a mask of bit fields indicating various processing options. 113Possible flags are: 114.Bl -tag -width DPV_NO_OVERRUN 115.It Dv DPV_TEST_MODE 116Enable test mode. 117In test mode, 118the 119.Fn action 120callback of the 121.Fa config 122argument is not called but instead simulated-data is used to drive progress. 123Appends 124.Dq [TEST MODE] 125to the status line 126.Po 127to override, 128set the 129.Va status_format 130member of the 131.Fn dpv 132.Fa config 133argument; 134for example, 135to 136.Dv DPV_STATUS_DEFAULT 137.Pc . 138.It Dv DPV_WIDE_MODE 139Enable wide mode. 140In wide mode, 141the length of the 142.Va aprompt 143and 144.Va pprompt 145members of the 146.Fn dpv 147.Fa config 148argument will bump the width of the gauge widget. 149Prompts wider than the maximum width will wrap 150.Po 151unless using 152.Xr Xdialog 1 Pq Pa ports/x11/xdialog ; 153see BUGS section below 154.Pc . 155.It Dv DPV_NO_LABELS 156Disables the display of labels associated with each transfer 157.Po 158.Va label_size 159member of 160.Fn dpv 161.Fa config 162argument is ignored 163.Pc . 164.It Dv DPV_USE_COLOR 165Force the use of color even if the 166.Va display_type 167does not support color 168.Po 169.Ev USE_COLOR 170environment variable is ignored 171.Pc . 172.It Dv DPV_NO_OVERRUN 173When enabled, 174callbacks for the current 175.Vt dpv_file_node 176are terminated when 177.Fn action 178returns 100 or greater 179.Po 180alleviates the need to change the 181.Va status 182of the current 183.Vt dpv_file_node 184but may also cause file truncation if the stream exceeds expected length 185.Pc . 186.El 187.Pp 188The 189.Fa file_list 190argument to 191.Fn dpv 192is a pointer to a 193.Dq linked-list , 194described in 195.In dpv.h : 196.Bd -literal -offset indent 197struct dpv_file_node { 198 enum dpv_status status; /* status of read operation */ 199 char *msg; /* display instead of "Done/Fail" */ 200 char *name; /* name of file to read */ 201 char *path; /* path to file */ 202 long long length; /* expected size */ 203 long long read; /* number units read (e.g., bytes) */ 204 struct dpv_file_node *next;/* pointer to next (end with NULL) */ 205}; 206.Ed 207.Pp 208For each of the items in the 209.Fa file_list 210.Dq linked-list 211argument, 212the 213.Fn action 214callback member of the 215.Fn dpv 216.Fa config 217argument is called. 218The 219.Fn action 220function performs a 221.Dq nominal 222action on the file and return. 223The return value of 224.Vt int 225represents the current progress percentage 226.Pq 0-100 227for the current file. 228.Pp 229The 230.Fn action 231callback provides two variables for each call. 232.Fa file 233provides a reference to the current 234.Vt dpv_file_node 235being processed. 236.Fa out 237provides a file descriptor where the data goes. 238.Pp 239If the 240.Va output 241member of the 242.Fn dpv 243.Fa config 244argument was set to DPV_OUTPUT_NONE 245.Pq default ; when invoking Fn dpv , 246the 247.Fa out 248file descriptor of 249.Fn action 250will be zero and can be ignored. 251If 252.Fa output 253was set to DPV_OUTPUT_FILE, 254.Fa out 255will be an open file descriptor to a file. 256If 257.Fa output 258was set to DPV_OUTPUT_SHELL, 259.Fa out 260will be an open file descriptor to a pipe for a spawned shell program. 261When 262.Fa out 263is greater than zero, 264write data that has been read back to 265.Fa out . 266.Pp 267To abort 268.Fn dpv , 269either from the 270.Fn action 271callback or asynchronously from a signal handler, 272two globals are provided via 273.In dpv.h : 274.Bd -literal -offset indent 275extern int dpv_interrupt; /* Set to TRUE in interrupt handler */ 276extern int dpv_abort; /* Set to true in callback to abort */ 277.Ed 278.Pp 279These globals are not automatically reset and must be manually maintained. 280Do not forget to reset these globals before subsequent invocations of 281.Fn dpv 282when making multiple calls from the same program. 283.Pp 284In addition, 285the 286.Va status 287member of the 288.Fn action 289.Fa file 290argument can be used to control callbacks for the current file. 291The 292.Va status 293member can be set to any of the below from 294.In dpv.h : 295.Bd -literal -offset indent 296enum dpv_status { 297 DPV_STATUS_RUNNING = 0, /* Running (default) */ 298 DPV_STATUS_DONE, /* Completed */ 299 DPV_STATUS_FAILED, /* Oops, something went wrong */ 300}; 301.Ed 302.Pp 303The default 304.Fa status 305is zero, 306DPV_STATUS_RUNNING, 307which keeps the callbacks coming for the current 308.Fn file . 309Setting 310.Ql file->status 311to anything other than DPV_STATUS_RUNNING will cause 312.Fn dpv 313to loop to the next file, 314effecting the next callback, 315if any. 316.Pp 317The 318.Fn action 319callback is responsible for calculating percentages and 320.Pq recommended 321maintaining a 322.Nm 323global counter so 324.Fn dpv 325can display throughput statistics. 326Percentages are reported through the 327.Vt int 328return value of the 329.Fn action 330callback. 331Throughput statistics are calculated from the below global 332.Vt int 333in 334.In dpv.h : 335.Bd -literal -offset indent 336extern int dpv_overall_read; 337.Ed 338.Pp 339Set this to the number of bytes that have been read for all files. 340Throughput information is displayed in the status line 341.Pq only available when using Xr dialog 3 342at the bottom of the screen. 343See DPV_DISPLAY_LIBDIALOG above. 344.Pp 345Note that 346.Va dpv_overall_read 347does not have to represent bytes. 348For example, 349the 350.Va status_format 351can be changed to display something other than 352.Dq Li bytes 353and increment 354.Va dpv_overall_read 355accordingly 356.Pq for example, counting lines . 357.Pp 358When 359.Fn dpv 360is processing the current file, 361the 362.Va length 363and 364.Va read 365members of the 366.Fn action 367.Fa file 368argument are used for calculating the display of mini progress bars 369.Po 370if enabled; 371see 372.Va pbar_size 373above 374.Pc . 375If the 376.Va length 377member of the current 378.Fa file 379is less than zero 380.Pq indicating an unknown file length , 381a 382.Xr humanize_number 3 383version of the 384.Va read 385member is used instead of a traditional progress bar. 386Otherwise a progress bar is calculated as percentage read to file length. 387.Fn action 388callback must maintain these member values for mini-progress bars. 389.Pp 390The 391.Fn dpv_free 392function performs 393.Xr free 3 394on private global variables initialized by 395.Fn dpv . 396.Sh ENVIRONMENT 397The below environment variables are referenced by 398.Nm : 399.Bl -tag -width ".Ev USE_COLOR" 400.It Ev DIALOG 401Override command string used to launch 402.Xr dialog 1 403.Pq requires Dv DPV_DISPLAY_DIALOG 404or 405.Xr Xdialog 1 Pq Pa ports/x11/xdialog 406.Pq requires Dv DPV_DISPLAY_XDIALOG ; 407default is either 408.Ql dialog 409.Pq for Dv DPV_DISPLAY_DIALOG 410or 411.Ql Xdialog 412.Pq for Dv DPV_DISPLAY_XDIALOG . 413.It Ev DIALOGRC 414If set and non-NULL, 415path to 416.Ql .dialogrc 417file. 418.It Ev HOME 419If 420.Ql Ev $DIALOGRC 421is either not set or NULL, 422used as a prefix to 423.Ql .dialogrc 424.Pq that is, Ql $HOME/.dialogrc . 425.It Ev USE_COLOR 426If set and NULL, 427disables the use of color when using 428.Xr dialog 1 . 429Does not apply to 430.Xr Xdialog 1 Pq Pa ports/x11/xdialog . 431.It Ev msg_done Ev msg_fail Ev msg_pending 432Internationalization strings for overriding the default English strings 433.Ql Done , 434.Ql Fail , 435and 436.Ql Pending 437respectively. 438To prevent their usage, 439explicitly set the 440.Va msg_done , 441.Va msg_fail , 442and 443.Va msg_pending 444members of 445.Fn dpv 446.Fa config 447argument to default macros 448.Pq DPV_DONE_DEFAULT, DPV_FAIL_DEFAULT, and DPV_PENDING_DEFAULT 449or desired values. 450.El 451.Sh FILES 452.Bl -tag -width ".Pa $HOME/.dialogrc" -compact 453.It Pa $HOME/.dialogrc 454.El 455.Sh SEE ALSO 456.Xr dialog 1 , 457.Xr Xdialog 1 Pq Pa ports/x11/xdialog , 458.Xr dialog 3 459.Sh HISTORY 460The 461.Nm 462library first appeared in 463.Fx 10.2 . 464.Sh AUTHORS 465.An Devin Teske Aq dteske@FreeBSD.org 466.Sh BUGS 467.Xr Xdialog 1 Pq Pa ports/x11/xdialog , 468when given both 469.Ql Fl -title Ar title 470.Po 471see above 472.Ql Va title 473member of 474.Va struct dpv_config 475.Pc 476and 477.Ql Fl -backtitle Ar backtitle 478.Po 479see above 480.Ql Va backtitle 481member of 482.Va struct dpv_config 483.Pc , 484displays the backtitle in place of the title and vice-versa. 485.Pp 486.Xr Xdialog 1 Pq Pa ports/x11/xdialog 487does not wrap long prompt texts received after initial launch. 488This is a known issue with the 489.Ql --gauge 490widget in 491.Xr Xdialog 1 Pq Pa ports/x11/xdialog . 492Embed escaped newlines within prompt text to force line breaks. 493.Pp 494.Xr dialog 1 495does not display the first character after a series of escaped escape-sequences 496(for example, ``\\\\n'' produces ``\\'' instead of ``\\n''). 497This is a known issue with 498.Xr dialog 1 499and does not affect 500.Xr dialog 3 501or 502.Xr Xdialog 1 Pq Pa ports/x11/xdialog . 503.Pp 504If an application ignores 505.Ev USE_COLOR 506when set and NULL before calling 507.Fn dpv 508with color escape sequences anyway, 509.Xr dialog 3 510and 511.Xr dialog 1 512may not render properly. 513Workaround is to detect when 514.Ev USE_COLOR 515is set and NULL and either not use color escape sequences at that time or use 516.Xr unsetenv 3 517to unset 518.Ev USE_COLOR , 519forcing interpretation of color sequences. 520This does not effect 521.Xr Xdialog 1 Pq Pa ports/x11/xdialog , 522which renders the color escape sequences as plain text. 523See 524.Do 525embedded "\\Z" sequences 526.Dc 527in 528.Xr dialog 1 529for additional information. 530