Commit 1173a0bdfc56a08eedafc06afcd37f0b35ac3ea2

Authored by Jay Berkenbilt
1 parent 17703a8d

Add --user-password, --owner-password, --bits to --encrypt

Add the command-line arguments. They don't do anything yet.
generate_auto_job
@@ -738,6 +738,11 @@ class Main: @@ -738,6 +738,11 @@ class Main:
738 738
739 if flag in expected: 739 if flag in expected:
740 options_seen.add(flag) 740 options_seen.add(flag)
  741 + elif flag.startswith('__'):
  742 + # This marks a flag that has no JSON equivalent because it
  743 + # is handled in some other fashion.
  744 + options_seen.add(flag[2:])
  745 + return
741 elif isinstance(j, str): 746 elif isinstance(j, str):
742 if not flag.startswith('_'): 747 if not flag.startswith('_'):
743 raise Exception(f'json: {flag} has a description' 748 raise Exception(f'json: {flag} has a description'
job.sums
1 # Generated by generate_auto_job 1 # Generated by generate_auto_job
2 -generate_auto_job 9abe2ec994fb98526f5e3c0c199ce2e61a868463cb522a5bc6e9730b65534187 2 +generate_auto_job bf44181b610d335511a41b6c2b9c3497d0b023a1ca2c8e4537b34cb6262ce173
3 include/qpdf/auto_job_c_att.hh 4c2b171ea00531db54720bf49a43f8b34481586ae7fb6cbf225099ee42bc5bb4 3 include/qpdf/auto_job_c_att.hh 4c2b171ea00531db54720bf49a43f8b34481586ae7fb6cbf225099ee42bc5bb4
4 include/qpdf/auto_job_c_copy_att.hh 50609012bff14fd82f0649185940d617d05d530cdc522185c7f3920a561ccb42 4 include/qpdf/auto_job_c_copy_att.hh 50609012bff14fd82f0649185940d617d05d530cdc522185c7f3920a561ccb42
5 include/qpdf/auto_job_c_enc.hh 28446f3c32153a52afa239ea40503e6cc8ac2c026813526a349e0cd4ae17ddd5 5 include/qpdf/auto_job_c_enc.hh 28446f3c32153a52afa239ea40503e6cc8ac2c026813526a349e0cd4ae17ddd5
6 include/qpdf/auto_job_c_main.hh dbfc221d1533120d1aa9c361d8d2483dea5fcb1c0fd95144d98d305e64ed32a6 6 include/qpdf/auto_job_c_main.hh dbfc221d1533120d1aa9c361d8d2483dea5fcb1c0fd95144d98d305e64ed32a6
7 include/qpdf/auto_job_c_pages.hh b3cc0f21029f6d89efa043dcdbfa183cb59325b6506001c18911614fe8e568ec 7 include/qpdf/auto_job_c_pages.hh b3cc0f21029f6d89efa043dcdbfa183cb59325b6506001c18911614fe8e568ec
8 include/qpdf/auto_job_c_uo.hh ae21b69a1efa9333050f4833d465f6daff87e5b38e5106e49bbef5d4132e4ed1 8 include/qpdf/auto_job_c_uo.hh ae21b69a1efa9333050f4833d465f6daff87e5b38e5106e49bbef5d4132e4ed1
9 -job.yml 1f5db325600a763692034835117ac6b1a4b6aba8e73faa13a004ddc086834545  
10 -libqpdf/qpdf/auto_job_decl.hh 7844eba58edffb9494b19e8eca6fd59a24d6e152ca606c3b07da569f753df2da  
11 -libqpdf/qpdf/auto_job_help.hh 319c7bd0bfe2f3cb96bb16b66a9331a81b312805a64acaad54737b5623773e31  
12 -libqpdf/qpdf/auto_job_init.hh e6c09e94c92bd17e9c728b11437e3c98266c93c42c3efbce050c8d288e6b3473 9 +job.yml 4f89fc7b622df897d30d403d8035aa36fc7de8d8c43042c736e0300d904cb05c
  10 +libqpdf/qpdf/auto_job_decl.hh 9c6f701c29f3f764d620186bed92685a2edf2e4d11e4f4532862c05470cfc4d2
  11 +libqpdf/qpdf/auto_job_help.hh 788320d439519ecd284621531e96ee698965a9ad342fd423c5fb1de75d2a06b1
  12 +libqpdf/qpdf/auto_job_init.hh b4c2b3724fba61f1206fd3bae81951636852592f67a63ef9539839c2c5995065
13 libqpdf/qpdf/auto_job_json_decl.hh 06caa46eaf71db8a50c046f91866baa8087745a9474319fb7c86d92634cc8297 13 libqpdf/qpdf/auto_job_json_decl.hh 06caa46eaf71db8a50c046f91866baa8087745a9474319fb7c86d92634cc8297
14 -libqpdf/qpdf/auto_job_json_init.hh 85ac7e5c66f14c767419823eac84bdea4bd72d690bfe12b533321e5708e644b7  
15 -libqpdf/qpdf/auto_job_schema.hh 5e0f5cb7d462716fe52548b2ae1a8eb6f3c900016e915140eea37f78cee45b2b 14 +libqpdf/qpdf/auto_job_json_init.hh f5acb9aa103131cb68dec0e12c4d237a6459bdb49b24773c24f0c2724a462b8f
  15 +libqpdf/qpdf/auto_job_schema.hh b53c006fec2e75b1b73588d242d49a32f7d3db820b1541de106c5d4c27fbb4d9
16 manual/_ext/qpdf.py 6add6321666031d55ed4aedf7c00e5662bba856dfcd66ccb526563bffefbb580 16 manual/_ext/qpdf.py 6add6321666031d55ed4aedf7c00e5662bba856dfcd66ccb526563bffefbb580
17 -manual/cli.rst 4f2806f7cf77f167fd41b065a8916f02fdfaab35ad1a74587578bf2954228464 17 +manual/cli.rst b524f96f2a6f338f3e4350703598c56ba22e8f12a8efb7a441648c6dbf0a455e
@@ -60,6 +60,10 @@ choices: @@ -60,6 +60,10 @@ choices:
60 - 1 60 - 1
61 - 2 61 - 2
62 - latest 62 - latest
  63 + enc_bits:
  64 + - 40
  65 + - 128
  66 + - 256
63 print128: 67 print128:
64 - full 68 - full
65 - low 69 - low
@@ -194,8 +198,18 @@ options: @@ -194,8 +198,18 @@ options:
194 required_parameter: 198 required_parameter:
195 password: password 199 password: password
196 - table: encryption 200 - table: encryption
  201 + config: c_main
197 prefix: Enc 202 prefix: Enc
198 positional: true 203 positional: true
  204 + manual:
  205 + - user-password
  206 + - owner-password
  207 + - bits
  208 + required_parameter:
  209 + user-password: user_password
  210 + owner-password: owner_password
  211 + required_choices:
  212 + bits: enc_bits
199 - table: 40-bit encryption 213 - table: 40-bit encryption
200 config: c_enc 214 config: c_enc
201 config_prefix: Enc 215 config_prefix: Enc
@@ -276,10 +290,14 @@ json: @@ -276,10 +290,14 @@ json:
276 # match a command-line option, and its properties and help come from 290 # match a command-line option, and its properties and help come from
277 # other information known by generate_auto_job. This information is 291 # other information known by generate_auto_job. This information is
278 # used to construct a "schema" (as in JSON.hh) for the json input to 292 # used to construct a "schema" (as in JSON.hh) for the json input to
279 - # QPDFJob. The leading underscore is removed. *NOTE*: all keys are  
280 - # converted to camelCase for the schema and must appear that way  
281 - # in the user-supplied json. This makes it more convenient to  
282 - # populate JSON objects in some languages. 293 + # QPDFJob. The leading underscore is removed. If a key starts with a
  294 + # double underscore, it corresponds to a command-line argument that
  295 + # does not have a counterpart in the JSON. This signals that the
  296 + # command-line argument was not forgotten, but it is otherwise
  297 + # ignored by the JSON. *NOTE*: all keys are converted to camelCase
  298 + # for the schema and must appear that way in the user-supplied json.
  299 + # This makes it more convenient to populate JSON objects in some
  300 + # languages.
283 301
284 # input 302 # input
285 _inputFile: "input filename" 303 _inputFile: "input filename"
@@ -316,8 +334,9 @@ json: @@ -316,8 +334,9 @@ json:
316 json-output: 334 json-output:
317 remove-restrictions: 335 remove-restrictions:
318 encrypt: 336 encrypt:
319 - _user-password: "user password"  
320 - _owner-password: "owner password" 337 + user-password:
  338 + owner-password:
  339 + __bits:
321 _40bit: 340 _40bit:
322 Enc40.annotate: 341 Enc40.annotate:
323 Enc40.extract: 342 Enc40.extract:
libqpdf/QPDFJob_argv.cc
@@ -204,6 +204,24 @@ ArgParser::argEncPositional(std::string const& arg) @@ -204,6 +204,24 @@ ArgParser::argEncPositional(std::string const& arg)
204 } 204 }
205 205
206 void 206 void
  207 +ArgParser::argEncUserPassword(std::string const& arg)
  208 +{
  209 + // QXXXQ
  210 +}
  211 +
  212 +void
  213 +ArgParser::argEncOwnerPassword(std::string const& arg)
  214 +{
  215 + // QXXXQ
  216 +}
  217 +
  218 +void
  219 +ArgParser::argEncBits(std::string const& arg)
  220 +{
  221 + // QXXXQ
  222 +}
  223 +
  224 +void
207 ArgParser::argPages() 225 ArgParser::argPages()
208 { 226 {
209 this->accumulated_args.clear(); 227 this->accumulated_args.clear();
libqpdf/QPDFJob_json.cc
@@ -109,6 +109,10 @@ Handlers::initHandlers() @@ -109,6 +109,10 @@ Handlers::initHandlers()
109 109
110 #include <qpdf/auto_job_json_init.hh> 110 #include <qpdf/auto_job_json_init.hh>
111 111
  112 + // We have `bits` in the CLI but not in the JSON. Reference this variable so it doesn't generate
  113 + // a warning.
  114 + [](char const**) {}(enc_bits_choices);
  115 +
112 if (this->json_handlers.size() != 1) { 116 if (this->json_handlers.size() != 1) {
113 throw std::logic_error("QPDFJob_json: json_handlers size != 1 at end"); 117 throw std::logic_error("QPDFJob_json: json_handlers size != 1 at end");
114 } 118 }
libqpdf/qpdf/auto_job_decl.hh
@@ -32,6 +32,9 @@ void argPagesPositional(std::string const&amp;); @@ -32,6 +32,9 @@ void argPagesPositional(std::string const&amp;);
32 void argPagesPassword(std::string const&); 32 void argPagesPassword(std::string const&);
33 void argEndPages(); 33 void argEndPages();
34 void argEncPositional(std::string const&); 34 void argEncPositional(std::string const&);
  35 +void argEncUserPassword(std::string const&);
  36 +void argEncOwnerPassword(std::string const&);
  37 +void argEncBits(std::string const&);
35 void argEndEncryption(); 38 void argEndEncryption();
36 void argEnd40BitEncryption(); 39 void argEnd40BitEncryption();
37 void argEnd128BitEncryption(); 40 void argEnd128BitEncryption();
libqpdf/qpdf/auto_job_help.hh
@@ -152,10 +152,25 @@ ap.addOptionHelp(&quot;--encrypt&quot;, &quot;transformation&quot;, &quot;start encryption options&quot;, R&quot;(- @@ -152,10 +152,25 @@ ap.addOptionHelp(&quot;--encrypt&quot;, &quot;transformation&quot;, &quot;start encryption options&quot;, R&quot;(-
152 152
153 Run qpdf --help=encryption for details. 153 Run qpdf --help=encryption for details.
154 )"); 154 )");
  155 +ap.addOptionHelp("--user-password", "transformation", "specify user password", R"(--user-password=user-password
  156 +
  157 +Set the user password.
  158 +)");
  159 +ap.addOptionHelp("--owner-password", "transformation", "specify owner password", R"(--owner-password=owner-password
  160 +
  161 +Set the owner password.
  162 +)");
  163 +ap.addOptionHelp("--bits", "transformation", "specify encryption bit depth", R"(--bits={48|128|256}
  164 +
  165 +Set the encrypt bit depth. Use 256.
  166 +)");
155 ap.addOptionHelp("--decrypt", "transformation", "remove encryption from input file", R"(Create an unencrypted output file even if the input file was 167 ap.addOptionHelp("--decrypt", "transformation", "remove encryption from input file", R"(Create an unencrypted output file even if the input file was
156 encrypted. Normally qpdf preserves whatever encryption was 168 encrypted. Normally qpdf preserves whatever encryption was
157 present on the input file. This option overrides that behavior. 169 present on the input file. This option overrides that behavior.
158 )"); 170 )");
  171 +}
  172 +static void add_help_3(QPDFArgParser& ap)
  173 +{
159 ap.addOptionHelp("--remove-restrictions", "transformation", "remove security restrictions from input file", R"(Remove restrictions associated with digitally signed PDF files. 174 ap.addOptionHelp("--remove-restrictions", "transformation", "remove security restrictions from input file", R"(Remove restrictions associated with digitally signed PDF files.
160 This may be combined with --decrypt to allow free editing of 175 This may be combined with --decrypt to allow free editing of
161 previously signed/encrypted files. This option invalidates the 176 previously signed/encrypted files. This option invalidates the
@@ -172,9 +187,6 @@ ap.addOptionHelp(&quot;--encryption-file-password&quot;, &quot;transformation&quot;, &quot;supply passwor @@ -172,9 +187,6 @@ ap.addOptionHelp(&quot;--encryption-file-password&quot;, &quot;transformation&quot;, &quot;supply passwor
172 If the file named in --copy-encryption requires a password, use 187 If the file named in --copy-encryption requires a password, use
173 this option to supply the password. 188 this option to supply the password.
174 )"); 189 )");
175 -}  
176 -static void add_help_3(QPDFArgParser& ap)  
177 -{  
178 ap.addOptionHelp("--qdf", "transformation", "enable viewing PDF code in a text editor", R"(Create a PDF file suitable for viewing in a text editor and even 190 ap.addOptionHelp("--qdf", "transformation", "enable viewing PDF code in a text editor", R"(Create a PDF file suitable for viewing in a text editor and even
179 editing. This is for editing the PDF code, not the page contents. 191 editing. This is for editing the PDF code, not the page contents.
180 All streams that can be uncompressed are uncompressed, and 192 All streams that can be uncompressed are uncompressed, and
@@ -270,6 +282,9 @@ ap.addOptionHelp(&quot;--ii-min-bytes&quot;, &quot;transformation&quot;, &quot;set minimum size for --ext @@ -270,6 +282,9 @@ ap.addOptionHelp(&quot;--ii-min-bytes&quot;, &quot;transformation&quot;, &quot;set minimum size for --ext
270 Don't externalize inline images smaller than this size. The 282 Don't externalize inline images smaller than this size. The
271 default is 1,024. Use 0 for no minimum. 283 default is 1,024. Use 0 for no minimum.
272 )"); 284 )");
  285 +}
  286 +static void add_help_4(QPDFArgParser& ap)
  287 +{
273 ap.addOptionHelp("--min-version", "transformation", "set minimum PDF version", R"(--min-version=version 288 ap.addOptionHelp("--min-version", "transformation", "set minimum PDF version", R"(--min-version=version
274 289
275 Force the PDF version of the output to be at least the specified 290 Force the PDF version of the output to be at least the specified
@@ -297,9 +312,6 @@ resulting set of pages, where :odd starts with the first page and @@ -297,9 +312,6 @@ resulting set of pages, where :odd starts with the first page and
297 :even starts with the second page. These are odd and even pages 312 :even starts with the second page. These are odd and even pages
298 from the resulting set, not based on the original page numbers. 313 from the resulting set, not based on the original page numbers.
299 )"); 314 )");
300 -}  
301 -static void add_help_4(QPDFArgParser& ap)  
302 -{  
303 ap.addHelpTopic("modification", "change parts of the PDF", R"(Modification options make systematic changes to certain parts of 315 ap.addHelpTopic("modification", "change parts of the PDF", R"(Modification options make systematic changes to certain parts of
304 the PDF, causing the PDF to render differently from the original. 316 the PDF, causing the PDF to render differently from the original.
305 )"); 317 )");
@@ -392,6 +404,9 @@ ap.addOptionHelp(&quot;--keep-inline-images&quot;, &quot;modification&quot;, &quot;exclude inline images @@ -392,6 +404,9 @@ ap.addOptionHelp(&quot;--keep-inline-images&quot;, &quot;modification&quot;, &quot;exclude inline images
392 )"); 404 )");
393 ap.addOptionHelp("--remove-page-labels", "modification", "remove explicit page numbers", R"(Exclude page labels (explicit page numbers) from the output file. 405 ap.addOptionHelp("--remove-page-labels", "modification", "remove explicit page numbers", R"(Exclude page labels (explicit page numbers) from the output file.
394 )"); 406 )");
  407 +}
  408 +static void add_help_5(QPDFArgParser& ap)
  409 +{
395 ap.addHelpTopic("encryption", "create encrypted files", R"(Create encrypted files. Usage: 410 ap.addHelpTopic("encryption", "create encrypted files", R"(Create encrypted files. Usage:
396 411
397 --encrypt user-password owner-password key-length [options] -- 412 --encrypt user-password owner-password key-length [options] --
@@ -467,9 +482,6 @@ and filling in form fields. For 128-bit and 256-bit encryption, @@ -467,9 +482,6 @@ and filling in form fields. For 128-bit and 256-bit encryption,
467 this also enables editing, creating, and deleting form fields 482 this also enables editing, creating, and deleting form fields
468 unless --modify-other=n or --modify=none is also specified. 483 unless --modify-other=n or --modify=none is also specified.
469 )"); 484 )");
470 -}  
471 -static void add_help_5(QPDFArgParser& ap)  
472 -{  
473 ap.addOptionHelp("--assemble", "encryption", "restrict document assembly", R"(--assemble=[y|n] 485 ap.addOptionHelp("--assemble", "encryption", "restrict document assembly", R"(--assemble=[y|n]
474 486
475 Enable/disable document assembly (rotation and reordering of 487 Enable/disable document assembly (rotation and reordering of
@@ -628,6 +640,9 @@ Specify pages from the overlay/underlay that are repeated after @@ -628,6 +640,9 @@ Specify pages from the overlay/underlay that are repeated after
628 "from" pages have been exhausted. See qpdf --help=page-ranges 640 "from" pages have been exhausted. See qpdf --help=page-ranges
629 for help with the page range syntax. 641 for help with the page range syntax.
630 )"); 642 )");
  643 +}
  644 +static void add_help_6(QPDFArgParser& ap)
  645 +{
631 ap.addHelpTopic("attachments", "work with embedded files", R"(It is possible to list, add, or delete embedded files (also known 646 ap.addHelpTopic("attachments", "work with embedded files", R"(It is possible to list, add, or delete embedded files (also known
632 as attachments) and to copy attachments from other files. See help 647 as attachments) and to copy attachments from other files. See help
633 on individual options for details. Run qpdf --help=add-attachment 648 on individual options for details. Run qpdf --help=add-attachment
@@ -645,9 +660,6 @@ The --copy-attachments-from flag and its options may be repeated @@ -645,9 +660,6 @@ The --copy-attachments-from flag and its options may be repeated
645 to copy attachments from multiple files. Run 660 to copy attachments from multiple files. Run
646 qpdf --help=copy-attachments for details. 661 qpdf --help=copy-attachments for details.
647 )"); 662 )");
648 -}  
649 -static void add_help_6(QPDFArgParser& ap)  
650 -{  
651 ap.addOptionHelp("--remove-attachment", "attachments", "remove an embedded file", R"(--remove-attachment=key 663 ap.addOptionHelp("--remove-attachment", "attachments", "remove an embedded file", R"(--remove-attachment=key
652 664
653 Remove an embedded file using its key. Get the key with 665 Remove an embedded file using its key. Get the key with
@@ -746,6 +758,9 @@ of the actual PDF page content or semantic correctness of the @@ -746,6 +758,9 @@ of the actual PDF page content or semantic correctness of the
746 PDF file. It merely checks that the PDF file is syntactically 758 PDF file. It merely checks that the PDF file is syntactically
747 valid. See also qpdf --help=exit-status. 759 valid. See also qpdf --help=exit-status.
748 )"); 760 )");
  761 +}
  762 +static void add_help_7(QPDFArgParser& ap)
  763 +{
749 ap.addOptionHelp("--show-encryption", "inspection", "information about encrypted files", R"(Show document encryption parameters. Also show the document's 764 ap.addOptionHelp("--show-encryption", "inspection", "information about encrypted files", R"(Show document encryption parameters. Also show the document's
750 user password if the owner password is given and the file was 765 user password if the owner password is given and the file was
751 encrypted using older encryption formats that allow user 766 encrypted using older encryption formats that allow user
@@ -757,9 +772,6 @@ underlying encryption key to be displayed. @@ -757,9 +772,6 @@ underlying encryption key to be displayed.
757 ap.addOptionHelp("--check-linearization", "inspection", "check linearization tables", R"(Check to see whether a file is linearized and, if so, whether 772 ap.addOptionHelp("--check-linearization", "inspection", "check linearization tables", R"(Check to see whether a file is linearized and, if so, whether
758 the linearization hint tables are correct. 773 the linearization hint tables are correct.
759 )"); 774 )");
760 -}  
761 -static void add_help_7(QPDFArgParser& ap)  
762 -{  
763 ap.addOptionHelp("--show-linearization", "inspection", "show linearization hint tables", R"(Check and display all data in the linearization hint tables. 775 ap.addOptionHelp("--show-linearization", "inspection", "show linearization hint tables", R"(Check and display all data in the linearization hint tables.
764 )"); 776 )");
765 ap.addOptionHelp("--show-xref", "inspection", "show cross reference data", R"(Show the contents of the cross-reference table or stream (object 777 ap.addOptionHelp("--show-xref", "inspection", "show cross reference data", R"(Show the contents of the cross-reference table or stream (object
@@ -840,6 +852,9 @@ object number. The prefix can be overridden with @@ -840,6 +852,9 @@ object number. The prefix can be overridden with
840 when --json-output is specified, in which case the default is 852 when --json-output is specified, in which case the default is
841 "inline". 853 "inline".
842 )"); 854 )");
  855 +}
  856 +static void add_help_8(QPDFArgParser& ap)
  857 +{
843 ap.addOptionHelp("--json-stream-prefix", "json", "prefix for json stream data files", R"(--json-stream-prefix=file-prefix 858 ap.addOptionHelp("--json-stream-prefix", "json", "prefix for json stream data files", R"(--json-stream-prefix=file-prefix
844 859
845 When used with --json-stream-data=file, --json-stream-data=file-prefix 860 When used with --json-stream-data=file, --json-stream-data=file-prefix
@@ -860,9 +875,6 @@ ap.addOptionHelp(&quot;--json-input&quot;, &quot;json&quot;, &quot;input file is qpdf JSON&quot;, R&quot;(Treat the @@ -860,9 +875,6 @@ ap.addOptionHelp(&quot;--json-input&quot;, &quot;json&quot;, &quot;input file is qpdf JSON&quot;, R&quot;(Treat the
860 "qpdf JSON Format" section of the manual for information about 875 "qpdf JSON Format" section of the manual for information about
861 how to use this option. 876 how to use this option.
862 )"); 877 )");
863 -}  
864 -static void add_help_8(QPDFArgParser& ap)  
865 -{  
866 ap.addOptionHelp("--update-from-json", "json", "update a PDF from qpdf JSON", R"(--update-from-json=qpdf-json-file 878 ap.addOptionHelp("--update-from-json", "json", "update a PDF from qpdf JSON", R"(--update-from-json=qpdf-json-file
867 879
868 Update a PDF file from a JSON file. Please see the "qpdf JSON" 880 Update a PDF file from a JSON file. Please see the "qpdf JSON"
libqpdf/qpdf/auto_job_init.hh
@@ -23,6 +23,7 @@ static char const* json_key_choices[] = {&quot;acroform&quot;, &quot;attachments&quot;, &quot;encrypt&quot;, &quot; @@ -23,6 +23,7 @@ static char const* json_key_choices[] = {&quot;acroform&quot;, &quot;attachments&quot;, &quot;encrypt&quot;, &quot;
23 static char const* json_output_choices[] = {"2", "latest", 0}; 23 static char const* json_output_choices[] = {"2", "latest", 0};
24 static char const* json_stream_data_choices[] = {"none", "inline", "file", 0}; 24 static char const* json_stream_data_choices[] = {"none", "inline", "file", 0};
25 static char const* json_version_choices[] = {"1", "2", "latest", 0}; 25 static char const* json_version_choices[] = {"1", "2", "latest", 0};
  26 +static char const* enc_bits_choices[] = {"40", "128", "256", 0};
26 static char const* print128_choices[] = {"full", "low", "none", 0}; 27 static char const* print128_choices[] = {"full", "low", "none", 0};
27 static char const* modify128_choices[] = {"all", "annotate", "form", "assembly", "none", 0}; 28 static char const* modify128_choices[] = {"all", "annotate", "form", "assembly", "none", 0};
28 29
@@ -128,6 +129,9 @@ this-&gt;ap.addPositional(p(&amp;ArgParser::argPagesPositional)); @@ -128,6 +129,9 @@ this-&gt;ap.addPositional(p(&amp;ArgParser::argPagesPositional));
128 this->ap.addRequiredParameter("password", p(&ArgParser::argPagesPassword), "password"); 129 this->ap.addRequiredParameter("password", p(&ArgParser::argPagesPassword), "password");
129 this->ap.registerOptionTable("encryption", b(&ArgParser::argEndEncryption)); 130 this->ap.registerOptionTable("encryption", b(&ArgParser::argEndEncryption));
130 this->ap.addPositional(p(&ArgParser::argEncPositional)); 131 this->ap.addPositional(p(&ArgParser::argEncPositional));
  132 +this->ap.addRequiredParameter("user-password", p(&ArgParser::argEncUserPassword), "user_password");
  133 +this->ap.addRequiredParameter("owner-password", p(&ArgParser::argEncOwnerPassword), "owner_password");
  134 +this->ap.addChoices("bits", p(&ArgParser::argEncBits), true, enc_bits_choices);
131 this->ap.registerOptionTable("40-bit encryption", b(&ArgParser::argEnd40BitEncryption)); 135 this->ap.registerOptionTable("40-bit encryption", b(&ArgParser::argEnd40BitEncryption));
132 this->ap.addChoices("extract", [this](std::string const& x){c_enc->extract(x);}, true, yn_choices); 136 this->ap.addChoices("extract", [this](std::string const& x){c_enc->extract(x);}, true, yn_choices);
133 this->ap.addChoices("annotate", [this](std::string const& x){c_enc->annotate(x);}, true, yn_choices); 137 this->ap.addChoices("annotate", [this](std::string const& x){c_enc->annotate(x);}, true, yn_choices);
libqpdf/qpdf/auto_job_json_init.hh
@@ -16,6 +16,7 @@ static char const* json_key_choices[] = {&quot;acroform&quot;, &quot;attachments&quot;, &quot;encrypt&quot;, &quot; @@ -16,6 +16,7 @@ static char const* json_key_choices[] = {&quot;acroform&quot;, &quot;attachments&quot;, &quot;encrypt&quot;, &quot;
16 static char const* json_output_choices[] = {"2", "latest", 0}; 16 static char const* json_output_choices[] = {"2", "latest", 0};
17 static char const* json_stream_data_choices[] = {"none", "inline", "file", 0}; 17 static char const* json_stream_data_choices[] = {"none", "inline", "file", 0};
18 static char const* json_version_choices[] = {"1", "2", "latest", 0}; 18 static char const* json_version_choices[] = {"1", "2", "latest", 0};
  19 +static char const* enc_bits_choices[] = {"40", "128", "256", 0};
19 static char const* print128_choices[] = {"full", "low", "none", 0}; 20 static char const* print128_choices[] = {"full", "low", "none", 0};
20 static char const* modify128_choices[] = {"all", "annotate", "form", "assembly", "none", 0}; 21 static char const* modify128_choices[] = {"all", "annotate", "form", "assembly", "none", 0};
21 22
@@ -120,6 +121,8 @@ popHandler(); // key: userPassword @@ -120,6 +121,8 @@ popHandler(); // key: userPassword
120 pushKey("ownerPassword"); 121 pushKey("ownerPassword");
121 setupEncryptOwnerPassword(); 122 setupEncryptOwnerPassword();
122 popHandler(); // key: ownerPassword 123 popHandler(); // key: ownerPassword
  124 +pushKey("Bits");
  125 +popHandler(); // key: Bits
123 pushKey("40bit"); 126 pushKey("40bit");
124 beginDict(bindJSON(&Handlers::beginEncrypt40bit), bindBare(&Handlers::endEncrypt40bit)); // .encrypt.40bit 127 beginDict(bindJSON(&Handlers::beginEncrypt40bit), bindBare(&Handlers::endEncrypt40bit)); // .encrypt.40bit
125 pushKey("annotate"); 128 pushKey("annotate");
libqpdf/qpdf/auto_job_schema.hh
@@ -31,8 +31,9 @@ static constexpr char const* JOB_SCHEMA_DATA = R&quot;({ @@ -31,8 +31,9 @@ static constexpr char const* JOB_SCHEMA_DATA = R&quot;({
31 "jsonOutput": "apply defaults for JSON serialization", 31 "jsonOutput": "apply defaults for JSON serialization",
32 "removeRestrictions": "remove security restrictions from input file", 32 "removeRestrictions": "remove security restrictions from input file",
33 "encrypt": { 33 "encrypt": {
34 - "userPassword": "user password",  
35 - "ownerPassword": "owner password", 34 + "userPassword": "specify user password",
  35 + "ownerPassword": "specify owner password",
  36 + "Bits": null,
36 "40bit": { 37 "40bit": {
37 "annotate": "restrict document annotation", 38 "annotate": "restrict document annotation",
38 "extract": "restrict text/graphic extraction", 39 "extract": "restrict text/graphic extraction",
manual/cli.rst
@@ -723,6 +723,32 @@ Related Options @@ -723,6 +723,32 @@ Related Options
723 This flag starts encryption options, used to create encrypted 723 This flag starts encryption options, used to create encrypted
724 files. Please see :ref:`encryption-options` for details. 724 files. Please see :ref:`encryption-options` for details.
725 725
  726 +.. qpdf:option:: --user-password=user-password
  727 +
  728 + .. help: specify user password
  729 +
  730 + Set the user password.
  731 +
  732 + Set the user password for the encrypted file.
  733 +
  734 +.. qpdf:option:: --owner-password=owner-password
  735 +
  736 + .. help: specify owner password
  737 +
  738 + Set the owner password.
  739 +
  740 + Set the owner password for the encrypted file.
  741 +
  742 +.. qpdf:option:: --bits={48|128|256}
  743 +
  744 + .. help: specify encryption bit depth
  745 +
  746 + Set the encrypt bit depth. Use 256.
  747 +
  748 + Set the bit depth for encrypted files. You should always use
  749 + ``--bits=256`` unless you have a strong reason to create a file
  750 + with weaker encryption.
  751 +
726 .. qpdf:option:: --decrypt 752 .. qpdf:option:: --decrypt
727 753
728 .. help: remove encryption from input file 754 .. help: remove encryption from input file