Question

Je voudrais savoir au sujet de la taille d'un tableau étant alloué en regardant le bytecode, si cette information est connue au moment de la compilation, bien sûr.

Arrière-plan: Je veux écrire un détecteur FindBugs (qui regarde le bytecode compilé) et de déclarer certaines occurences des allocations de tableaux. Pour filtrer les faux positifs, je ne suis pas intéressé par les tableaux « petits », mais seulement ceux dont la taille ne sont pas disponibles au moment de la compilation ou qui sont supérieures à un seuil configurable.

Comme le code source FindBugs est pas trop fortement documenté, je suis à la recherche de quelques conseils sur la façon de commencer - peut-être il y a un Dectector faire quelque chose de similaire déjà que je pourrais regarder

.
Était-ce utile?

La solution

Cela pourrait obtenir une sorte de délicate. Ma connaissance est incomplète, mais vous aurez au moins trois types d'instructions pour regarder dehors pour (newArray, ANEWARRAY et MULTIANEWARRAY). En regardant l'instruction précédente (ou dans le cas de MULTIANEWARRAY, n instructions précédentes) obtient la taille, qui même si elle était une constante peut être chargé avec BIPUSH, SIPUSH ou LDC (quoi que ce soit d'autre?) Selon la taille. Comme vous l'avez remarqué, si la classe est le résultat d'un calcul, vous pouvez être en train de tracer des instructions de retour indéfiniment.

Si je me souviens bien, FindBugs utilise la BCEL en interne, mais je ne l'ai jamais creusé autour de là-bas pour voir exactement comment intelligent qu'ils sont. Si l'une de ces équipes ont des listes de diffusion appropriées, ils peuvent se révéler un meilleur endroit pour demander -. Ils vont probablement au moins savoir si quelqu'un a été dans cette voie avant

Autres conseils

Eh bien, si elles sont attribuées en fonction d'une constante, vous pouvez vérifier une constante qui a été poussé juste avant l'allocation. Par exemple:

class ArraySize {
    private static final int smallsize = 10;
    private static final int largesize = 1000;
    public static void main(String[] args) {
        int[] small = new int[smallsize];
        int[] big = new int[largesize];
    }
}

donne le bytecode:

Compiled from "ArraySize.java"
class ArraySize extends java.lang.Object{
ArraySize();
  Code:
   0:   aload_0
   1:   invokespecial   #1; //Method java/lang/Object."<init>":()V
   4:   return

public static void main(java.lang.String[]);
  Code:
   0:   bipush  10
   2:   newarray int
   4:   astore_1
   5:   sipush  1000
   8:   newarray int
   10:  astore_2
   11:  return

}
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top