Commit 3a42f63a51b8957529d7013bb429345964030612

Authored by m-holger
1 parent 9e466084

In QPDFJob refactor output file handling to use std::string instead of shared_ptr<char>

Replaced shared_ptr<char> with std::string for `outfilename` in QPDFJob, simplifying its usage and reducing unnecessary memory management overhead. Updated related conditional checks and logic to align with the updated type. These changes improve code readability and maintainability.
include/qpdf/QPDFJob.hh
@@ -712,7 +712,7 @@ class QPDFJob @@ -712,7 +712,7 @@ class QPDFJob
712 bool check_is_encrypted{false}; 712 bool check_is_encrypted{false};
713 bool check_requires_password{false}; 713 bool check_requires_password{false};
714 std::shared_ptr<char> infilename; 714 std::shared_ptr<char> infilename;
715 - std::shared_ptr<char> outfilename; 715 + std::string outfilename;
716 bool json_input{false}; 716 bool json_input{false};
717 bool json_output{false}; 717 bool json_output{false};
718 std::string update_from_json; 718 std::string update_from_json;
libqpdf/QPDFJob.cc
@@ -561,7 +561,7 @@ QPDFJob::hasWarnings() const @@ -561,7 +561,7 @@ QPDFJob::hasWarnings() const
561 bool 561 bool
562 QPDFJob::createsOutput() const 562 QPDFJob::createsOutput() const
563 { 563 {
564 - return ((m->outfilename != nullptr) || m->replace_input); 564 + return (!m->outfilename.empty() || m->replace_input);
565 } 565 }
566 566
567 int 567 int
@@ -604,7 +604,7 @@ QPDFJob::checkConfiguration() @@ -604,7 +604,7 @@ QPDFJob::checkConfiguration()
604 604
605 if (m->replace_input) { 605 if (m->replace_input) {
606 // Check for --empty appears later after we have checked m->infilename. 606 // Check for --empty appears later after we have checked m->infilename.
607 - if (m->outfilename) { 607 + if (!m->outfilename.empty()) {
608 usage("--replace-input may not be used when an output file is specified"); 608 usage("--replace-input may not be used when an output file is specified");
609 } 609 }
610 if (m->split_pages) { 610 if (m->split_pages) {
@@ -614,10 +614,10 @@ QPDFJob::checkConfiguration() @@ -614,10 +614,10 @@ QPDFJob::checkConfiguration()
614 usage("--json may not be used with --replace-input"); 614 usage("--json may not be used with --replace-input");
615 } 615 }
616 } 616 }
617 - if (m->json_version && !m->outfilename) { 617 + if (m->json_version && m->outfilename.empty()) {
618 // The output file is optional with --json for backward compatibility and defaults to 618 // The output file is optional with --json for backward compatibility and defaults to
619 // standard output. 619 // standard output.
620 - m->outfilename = QUtil::make_shared_cstr("-"); 620 + m->outfilename = "-";
621 } 621 }
622 if (!m->infilename) { 622 if (!m->infilename) {
623 usage("an input file name is required"); 623 usage("an input file name is required");
@@ -625,10 +625,10 @@ QPDFJob::checkConfiguration() @@ -625,10 +625,10 @@ QPDFJob::checkConfiguration()
625 if (m->replace_input && (strlen(m->infilename.get()) == 0)) { 625 if (m->replace_input && (strlen(m->infilename.get()) == 0)) {
626 usage("--replace-input may not be used with --empty"); 626 usage("--replace-input may not be used with --empty");
627 } 627 }
628 - if (m->require_outfile && (m->outfilename == nullptr) && (!m->replace_input)) { 628 + if (m->require_outfile && m->outfilename.empty() && !m->replace_input) {
629 usage("an output file name is required; use - for standard output"); 629 usage("an output file name is required; use - for standard output");
630 } 630 }
631 - if ((!m->require_outfile) && ((m->outfilename != nullptr) || m->replace_input)) { 631 + if (!m->require_outfile && (!m->outfilename.empty() || m->replace_input)) {
632 usage("no output file may be given for this option"); 632 usage("no output file may be given for this option");
633 } 633 }
634 if (m->check_requires_password && m->check_is_encrypted) { 634 if (m->check_requires_password && m->check_is_encrypted) {
@@ -649,7 +649,7 @@ QPDFJob::checkConfiguration() @@ -649,7 +649,7 @@ QPDFJob::checkConfiguration()
649 } 649 }
650 650
651 bool save_to_stdout = false; 651 bool save_to_stdout = false;
652 - if (m->require_outfile && m->outfilename && (strcmp(m->outfilename.get(), "-") == 0)) { 652 + if (m->require_outfile && m->outfilename == "-") {
653 if (m->split_pages) { 653 if (m->split_pages) {
654 usage("--split-pages may not be used when writing to standard output"); 654 usage("--split-pages may not be used when writing to standard output");
655 } 655 }
@@ -661,7 +661,7 @@ QPDFJob::checkConfiguration() @@ -661,7 +661,7 @@ QPDFJob::checkConfiguration()
661 if (save_to_stdout) { 661 if (save_to_stdout) {
662 m->log->saveToStandardOutput(true); 662 m->log->saveToStandardOutput(true);
663 } 663 }
664 - if (!m->split_pages && QUtil::same_file(m->infilename.get(), m->outfilename.get())) { 664 + if (!m->split_pages && QUtil::same_file(m->infilename.get(), m->outfilename.data())) {
665 QTC::TC("qpdf", "QPDFJob same file error"); 665 QTC::TC("qpdf", "QPDFJob same file error");
666 usage( 666 usage(
667 "input file and output file are the same; use --replace-input to intentionally " 667 "input file and output file are the same; use --replace-input to intentionally "
@@ -2999,7 +2999,8 @@ QPDFJob::setWriterOptions(QPDFWriter&amp; w) @@ -2999,7 +2999,8 @@ QPDFJob::setWriterOptions(QPDFWriter&amp; w)
2999 std::shared_ptr<QPDFWriter::ProgressReporter>( 2999 std::shared_ptr<QPDFWriter::ProgressReporter>(
3000 new QPDFWriter::FunctionProgressReporter(m->progress_handler))); 3000 new QPDFWriter::FunctionProgressReporter(m->progress_handler)));
3001 } else { 3001 } else {
3002 - char const* outfilename = m->outfilename ? m->outfilename.get() : "standard output"; 3002 + char const* outfilename =
  3003 + !m->outfilename.empty() ? m->outfilename.data() : "standard output";
3003 w.registerProgressReporter( 3004 w.registerProgressReporter(
3004 std::shared_ptr<QPDFWriter::ProgressReporter>( 3005 std::shared_ptr<QPDFWriter::ProgressReporter>(
3005 // line-break 3006 // line-break
@@ -3014,20 +3015,20 @@ QPDFJob::doSplitPages(QPDF&amp; pdf) @@ -3014,20 +3015,20 @@ QPDFJob::doSplitPages(QPDF&amp; pdf)
3014 // Generate output file pattern 3015 // Generate output file pattern
3015 std::string before; 3016 std::string before;
3016 std::string after; 3017 std::string after;
3017 - size_t len = strlen(m->outfilename.get());  
3018 - char* num_spot = strstr(const_cast<char*>(m->outfilename.get()), "%d");  
3019 - if (num_spot != nullptr) { 3018 + size_t len = m->outfilename.size();
  3019 + auto num_spot = m->outfilename.find("%d");
  3020 + if (num_spot != std::string::npos) {
3020 QTC::TC("qpdf", "QPDFJob split-pages %d"); 3021 QTC::TC("qpdf", "QPDFJob split-pages %d");
3021 - before = std::string(m->outfilename.get(), QIntC::to_size(num_spot - m->outfilename.get()));  
3022 - after = num_spot + 2; 3022 + before = m->outfilename.substr(0, num_spot);
  3023 + after = m->outfilename.substr(num_spot + 2);
3023 } else if ( 3024 } else if (
3024 - (len >= 4) && (QUtil::str_compare_nocase(m->outfilename.get() + len - 4, ".pdf") == 0)) { 3025 + len >= 4 && QUtil::str_compare_nocase(m->outfilename.substr(len - 4).data(), ".pdf") == 0) {
3025 QTC::TC("qpdf", "QPDFJob split-pages .pdf"); 3026 QTC::TC("qpdf", "QPDFJob split-pages .pdf");
3026 - before = std::string(m->outfilename.get(), len - 4) + "-";  
3027 - after = m->outfilename.get() + len - 4; 3027 + before = std::string(m->outfilename.data(), len - 4) + "-";
  3028 + after = m->outfilename.data() + len - 4;
3028 } else { 3029 } else {
3029 QTC::TC("qpdf", "QPDFJob split-pages other"); 3030 QTC::TC("qpdf", "QPDFJob split-pages other");
3030 - before = std::string(m->outfilename.get()) + "-"; 3031 + before = m->outfilename + "-";
3031 } 3032 }
3032 3033
3033 if (shouldRemoveUnreferencedResources(pdf)) { 3034 if (shouldRemoveUnreferencedResources(pdf)) {
@@ -3101,15 +3102,15 @@ QPDFJob::doSplitPages(QPDF&amp; pdf) @@ -3101,15 +3102,15 @@ QPDFJob::doSplitPages(QPDF&amp; pdf)
3101 void 3102 void
3102 QPDFJob::writeOutfile(QPDF& pdf) 3103 QPDFJob::writeOutfile(QPDF& pdf)
3103 { 3104 {
3104 - std::shared_ptr<char> temp_out; 3105 + std::string temp_out;
3105 if (m->replace_input) { 3106 if (m->replace_input) {
3106 // Append but don't prepend to the path to generate a temporary name. This saves us from 3107 // Append but don't prepend to the path to generate a temporary name. This saves us from
3107 // having to split the path by directory and non-directory. 3108 // having to split the path by directory and non-directory.
3108 - temp_out = QUtil::make_shared_cstr(std::string(m->infilename.get()) + ".~qpdf-temp#"); 3109 + temp_out = std::string(m->infilename.get()) + ".~qpdf-temp#";
3109 // m->outfilename will be restored to 0 before temp_out goes out of scope. 3110 // m->outfilename will be restored to 0 before temp_out goes out of scope.
3110 m->outfilename = temp_out; 3111 m->outfilename = temp_out;
3111 - } else if (strcmp(m->outfilename.get(), "-") == 0) {  
3112 - m->outfilename = nullptr; 3112 + } else if (m->outfilename == "-") {
  3113 + m->outfilename.clear();
3113 } 3114 }
3114 if (m->json_version) { 3115 if (m->json_version) {
3115 writeJSON(pdf); 3116 writeJSON(pdf);
@@ -3117,8 +3118,8 @@ QPDFJob::writeOutfile(QPDF&amp; pdf) @@ -3117,8 +3118,8 @@ QPDFJob::writeOutfile(QPDF&amp; pdf)
3117 // QPDFWriter must have block scope so the output file will be closed after write() 3118 // QPDFWriter must have block scope so the output file will be closed after write()
3118 // finishes. 3119 // finishes.
3119 QPDFWriter w(pdf); 3120 QPDFWriter w(pdf);
3120 - if (m->outfilename) {  
3121 - w.setOutputFilename(m->outfilename.get()); 3121 + if (!m->outfilename.empty()) {
  3122 + w.setOutputFilename(m->outfilename.data());
3122 } else { 3123 } else {
3123 // saveToStandardOutput has already been called, but calling it again is defensive and 3124 // saveToStandardOutput has already been called, but calling it again is defensive and
3124 // harmless. 3125 // harmless.
@@ -3128,13 +3129,13 @@ QPDFJob::writeOutfile(QPDF&amp; pdf) @@ -3128,13 +3129,13 @@ QPDFJob::writeOutfile(QPDF&amp; pdf)
3128 setWriterOptions(w); 3129 setWriterOptions(w);
3129 w.write(); 3130 w.write();
3130 } 3131 }
3131 - if (m->outfilename) { 3132 + if (!m->outfilename.empty()) {
3132 doIfVerbose([&](Pipeline& v, std::string const& prefix) { 3133 doIfVerbose([&](Pipeline& v, std::string const& prefix) {
3133 - v << prefix << ": wrote file " << m->outfilename.get() << "\n"; 3134 + v << prefix << ": wrote file " << m->outfilename << "\n";
3134 }); 3135 });
3135 } 3136 }
3136 if (m->replace_input) { 3137 if (m->replace_input) {
3137 - m->outfilename = nullptr; 3138 + m->outfilename.clear();
3138 } 3139 }
3139 if (m->replace_input) { 3140 if (m->replace_input) {
3140 // We must close the input before we can rename files 3141 // We must close the input before we can rename files
@@ -3145,7 +3146,7 @@ QPDFJob::writeOutfile(QPDF&amp; pdf) @@ -3145,7 +3146,7 @@ QPDFJob::writeOutfile(QPDF&amp; pdf)
3145 backup.append(1, '#'); 3146 backup.append(1, '#');
3146 } 3147 }
3147 QUtil::rename_file(m->infilename.get(), backup.c_str()); 3148 QUtil::rename_file(m->infilename.get(), backup.c_str());
3148 - QUtil::rename_file(temp_out.get(), m->infilename.get()); 3149 + QUtil::rename_file(temp_out.data(), m->infilename.get());
3149 if (warnings) { 3150 if (warnings) {
3150 *m->log->getError() << m->message_prefix 3151 *m->log->getError() << m->message_prefix
3151 << ": there are warnings; original file kept in " << backup << "\n"; 3152 << ": there are warnings; original file kept in " << backup << "\n";
@@ -3167,12 +3168,12 @@ QPDFJob::writeJSON(QPDF&amp; pdf) @@ -3167,12 +3168,12 @@ QPDFJob::writeJSON(QPDF&amp; pdf)
3167 // File pipeline must have block scope so it will be closed after write. 3168 // File pipeline must have block scope so it will be closed after write.
3168 std::shared_ptr<QUtil::FileCloser> fc; 3169 std::shared_ptr<QUtil::FileCloser> fc;
3169 std::shared_ptr<Pipeline> fp; 3170 std::shared_ptr<Pipeline> fp;
3170 - if (m->outfilename.get()) { 3171 + if (!m->outfilename.empty()) {
3171 QTC::TC("qpdf", "QPDFJob write json to file"); 3172 QTC::TC("qpdf", "QPDFJob write json to file");
3172 if (m->json_stream_prefix.empty()) { 3173 if (m->json_stream_prefix.empty()) {
3173 - m->json_stream_prefix = m->outfilename.get(); 3174 + m->json_stream_prefix = m->outfilename;
3174 } 3175 }
3175 - fc = std::make_shared<QUtil::FileCloser>(QUtil::safe_fopen(m->outfilename.get(), "w")); 3176 + fc = std::make_shared<QUtil::FileCloser>(QUtil::safe_fopen(m->outfilename.data(), "w"));
3176 fp = std::make_shared<Pl_StdioFile>("json output", fc->f); 3177 fp = std::make_shared<Pl_StdioFile>("json output", fc->f);
3177 } else if ((m->json_stream_data == qpdf_sj_file) && m->json_stream_prefix.empty()) { 3178 } else if ((m->json_stream_data == qpdf_sj_file) && m->json_stream_prefix.empty()) {
3178 QTC::TC("qpdf", "QPDFJob need json-stream-prefix for stdout"); 3179 QTC::TC("qpdf", "QPDFJob need json-stream-prefix for stdout");
libqpdf/QPDFJob_config.cc
@@ -42,8 +42,8 @@ QPDFJob::Config::emptyInput() @@ -42,8 +42,8 @@ QPDFJob::Config::emptyInput()
42 QPDFJob::Config* 42 QPDFJob::Config*
43 QPDFJob::Config::outputFile(std::string const& filename) 43 QPDFJob::Config::outputFile(std::string const& filename)
44 { 44 {
45 - if ((o.m->outfilename == nullptr) && (!o.m->replace_input)) {  
46 - o.m->outfilename = QUtil::make_shared_cstr(filename); 45 + if (o.m->outfilename.empty() && !o.m->replace_input) {
  46 + o.m->outfilename = filename;
47 } else { 47 } else {
48 usage("output file has already been given"); 48 usage("output file has already been given");
49 } 49 }
@@ -53,7 +53,7 @@ QPDFJob::Config::outputFile(std::string const&amp; filename) @@ -53,7 +53,7 @@ QPDFJob::Config::outputFile(std::string const&amp; filename)
53 QPDFJob::Config* 53 QPDFJob::Config*
54 QPDFJob::Config::replaceInput() 54 QPDFJob::Config::replaceInput()
55 { 55 {
56 - if ((o.m->outfilename == nullptr) && (!o.m->replace_input)) { 56 + if (o.m->outfilename.empty() && !o.m->replace_input) {
57 o.m->replace_input = true; 57 o.m->replace_input = true;
58 } else { 58 } else {
59 usage("replace-input can't be used since output file has already been given"); 59 usage("replace-input can't be used since output file has already been given");