5

変数にメモリ内の必要なアドレスを割り当てることは可能ですか?

そうしようとしましたが、「割り当ての左オペランドとして左辺値が必要です」というエラーが表示されます。

int main() {
  int i = 10;
  &i = 7200;
  printf("i=%d address=%u", i, &i);
}

私のアプローチの何が問題になっていますか?C で、必要なアドレスを変数に割り当てる方法はありますか?

4

9 に答える 9

5

直接ではありません。ただし、これを行うことができます: int* i = 7200; .. そして i (つまり *i = 10) を使用しますが、クラッシュする可能性が高くなります。これは、低レベルの開発 (既知のメモリ アドレスを使用するデバイス ドライバーなど) を行う場合にのみ意味があります。

于 2012-11-26T05:19:47.660 に答える
3

C言語では、特定のメモリアドレスに名前を「付ける」手段はありません。つまり、特定の変数名が特定のアドレスにある左辺値を参照することになっていることを言語に伝えることはできません。したがって、述べたように、あなたの質問に対する答えは「いいえ」です。物語の終わり。

さらに、正式に言えば、Cで特定の数値アドレスを操作するための代替のポータブルな方法はありません。言語自体は、それを行うのに役立つ機能を定義していません。

ただし、特定の実装では、特定のアドレスにアクセスする手段が提供される場合があります。一般的な実装では、整数値Aをポインター型に変換すると、アドレスを指すポインターが作成されますA。そのようなポインタを逆参照することにより、そのメモリ位置にアクセスできます。

于 2012-11-26T05:27:02.210 に答える
3

最新のオペレーティングシステムでx86タイプのプロセッサを使用していると仮定すると、メモリの場所に書き込むことはできません。CPUはOSと連携してメモリを保護し、あるプロセスが誤って(または意図的に)別のプロセスのメモリを上書きしないようにします。これを許可すると、セキュリティ上のリスクが発生します(バッファオーバーフローを参照)。とにかくしようとすると、OS / CPUがこれを行うことができないため、「セグメンテーション違反」エラーが発生します。

これに関する技術的な詳細については、1、2、および3から始めます

代わりに、を使用して書き込み可能なメモリ位置を指定するようにOSに要求しますmalloc。この場合、OSカーネル(通常、任意のメモリ位置への書き込み許可されている唯一のプロセス)は、メモリの空き領域を見つけて、それをプロセスに割り当てます。割り当てプロセスは、メモリのその領域をプロセスに属するものとしてマークし、読み取りと書き込みができるようにします。

ただし、OS /プロセッサのアーキテクチャ/構成が異なると、任意の場所に書き込むことができます。その場合、このコードは機能します。

#include <stdio.h>
void main() {
  int *ptr;
  ptr = (int*)7000;
  *ptr = 10;
  printf("Value: %i", *ptr);
}
于 2012-11-26T05:28:31.083 に答える
1

ポータブルではありません。ただし、一部のコンパイラ (通常は組み込みの世界向け) には、それを行うための拡張機能があります。

たとえば、IAR コンパイラ (ここでは MSP430 用) では、次のように実行できます。

static const char version[] @ 0x1000 = "v1.0";

これにより、オブジェクトversionがメモリ アドレスに配置されます0x1000

于 2012-11-26T05:18:58.630 に答える
0

&aの「&」はコンパイル時にiのアドレスを評価しますが、これは仮想アドレスだと思います。したがって、コンパイラによると、これは左辺値ではありません。代わりにポインタを使用してください

于 2012-11-26T05:34:54.853 に答える
0

それは不可能です。コンパイラの拡張機能で可能かもしれません。ただし、必要なアドレスでメモリにアクセスできます (アドレスがプロセスにアクセスできる場合)。

int addr = 7200;
*((int*)addr) = newVal;
于 2012-11-26T05:22:32.877 に答える
0

いいえ。

できたとしても、7200 はポインター (メモリ アドレス) ではなく、int であるため、とにかく機能しません。

于 2012-11-26T05:17:13.170 に答える
0

変数が持つアドレスを特定する方法はおそらくありません。しかし、最後の希望として、「ポインター」と呼ばれるものがあり、アドレスの値を変更できます7200(ただし、このアドレスにはおそらくアクセスできません)。

int *i = (int *)7200;
*i = 10;
于 2012-11-26T05:19:27.260 に答える
0

ldscript/linker コマンド ファイルを使用します。ただし、これは実行時ではなくリンク時に割り当てられます。

リンカ コマンド ファイルの構文は、特定のコンパイラに大きく依存します。そのため、コンパイラのリンカー コマンド ファイルをグーグルで検索する必要があります。

おおよその疑似構文は次のようになります。

In linker command file:
.section start=0x1000 lenth=0x100 myVariables
In C file:
#pragma section myVariables
int myVar=10;
于 2012-11-26T05:20:06.823 に答える