C++ で動的にロードされるライブラリを作成しています。
コード内から (デバッグ上の理由で) argc と argv を読み取りたいのですが、main 関数にアクセスできません。コマンド ラインを取得する方法はありますか (Windows と Linux の両方のソリューションが適しています)。
ありがとう、ダン
C++ で動的にロードされるライブラリを作成しています。
コード内から (デバッグ上の理由で) argc と argv を読み取りたいのですが、main 関数にアクセスできません。コマンド ラインを取得する方法はありますか (Windows と Linux の両方のソリューションが適しています)。
ありがとう、ダン
Linux では、疑似ファイル /proc/self/cmdline にプロセスのコマンド ラインが保持されます。各引数は 0 バイトで終了し、最後の引数の後に追加の 0 バイトが続きます。
Win32 API には GetCommandLine() 関数があります。他のプラットフォームでは、argc/argv をどこかに保存する必要があります (外部変数?)。
Windows では、__argc および __argv を介して argc/argv にアクセスできます。ワイド文字バージョンが必要な場合は __wargv。
このスレッドは、Linux でそれを行う方法を示しています。
http://linux.derkeiler.com/Newsgroups/comp.os.linux.development.system/2005-07/0147.html
これは奇妙な状況のように聞こえるかもしれません。プラグインか何かを書いていますか?argv/argc にアクセスしてはいけませんか?
Windows では、GetCommandLine()を使用してコマンド ラインへのポインターを取得し、CommandLineToArgvW()を使用してそのポインターを argv[] 形式に変換できます。ただし、利用できるのはワイド (Unicode) バージョンのみです。
Windows では、次のようなものを使用して引数を取得します。
#include <windows.h>
#include <string>
#include <vector>
#include <cwchar>
#include <cstdio>
#include <clocale>
using namespace std;
vector<wstring> getArgs() {
int argc;
wchar_t** argv = CommandLineToArgvW(GetCommandLineW(), &argc);
vector<wstring> args;
if (argv) {
args.assign(argv, argv + argc);
LocalFree(argv);
}
return args;
}
int main() {
const vector<wstring> argv = getArgs();
setlocale(LC_CTYPE, ".OCP");
for (vector<wstring>::const_iterator i = argv.begin(); i != argv.end(); ++i) {
wprintf(L"%s\n", i->c_str());
}
}
編集:mingwはwmain()をサポートしていないため、そのようなgetArgs関数はmingwにも役立ちます。
これは Linux で動作するはずです:
#include <stdio.h>
#include <unistd.h>
void findargs(int *argc, char ***argv) {
size_t i;
char **p = &__environ[-2];
for (i = 1; i != *(size_t*)(p-1); i++) {
p--;
}
*argc = (int)i;
*argv = p;
}
int main(int argc, char **argv) {
printf("got argc=%d, argv=%p\n", argc, argv);
findargs(&argc, &argv);
printf("found argc=%d, argv=%p\n", argc, argv);
return 0;
}
注: setenv() が呼び出された場合は失敗します。
getpid()およびpsコマンドを使用します。
int pid;
int fd;
char cmd [80];
pid = getpid();
sprintf(cmd、 "ps%d"、pid);
fd = popen(cmd、 "r");
....行は次のようになります
.... 1358 ./a.out abc def
コマンドラインの代わりに環境変数を使用することを考えたことはありますか? ライブラリが使用されるアプリケーションの種類によっては、ユーザーにとってより簡単な場合があり、標準の getenv() 関数を使用できます。
いずれにせよ、あなたのライブラリが argc と argv を使用する場合、プログラムはそれらを渡すものであるべきだと思います。