Frage

Ich habe einige C # -Code in einen nicht verwalteten C ++ DLL aufrufen. Die Methode, die ich ist nenne soll eine Zeichenfolge als ref akzeptieren. Um damit umzugehen ich in einem String passieren, sonst gibt es eine Stackoverflow.

Das funktioniert gut, aber auf einigen Anrufen die Zeichenfolge, die wieder aus dem nicht verwalteten Code kommt, ist eine wirre Zeichenfolge wie folgt:. ØŸE, Ê. Ich weiß, das etwas mit Codierung zu tun haben muss, aber ich habe einige Dinge ausprobiert, die unten aufgeführt, und nichts funktioniert. Dies ist kein Problem in VB.Net Code, dass jemand anderes geschrieben hat etwas Ähnliches zu tun.

Hier ist, was ich versucht habe: 1. Ich bin mit dieser: [DllImport ( "dmphnx32.dll")], sondern haben versucht, alle Charset Optionen ohne Erfolg

.
  1. Versuchte zu verwenden Encoding.Default.GetBytes, Encoding.ASCII, Encoding.Unicode, und den Rest ohne Erfolg.

Ich habe keine Erfahrung mit C ++, so kann ich wirklich Hilfe gebrauchen.

Hier ist die DllImport Methode:

[DllImport("dmphnx32.dll")]
        public static extern int PhxQueryDataAttributes(int handle,
                                        StringBuilder lTableName,
                                        StringBuilder lColumnName,
                                        ref short lIteration,
                                        ref short type,
                                        ref short maxLen,
                                        ref short endorsement,
                                        StringBuilder endorsementId);

Hier ist der C ++ Code:

short DMEXP PhxQueryDataAttributes(HWND handle,
                                   char *lTableName,
                                   char *lColumnName,
                                   short *lIteration,
                                   short *Type,
                                   short *MaxLen,
                                   short *Endorsement,
                                   char  *EndorsementID)
{

    handle = PhxInfo.HiddenHwnd;
    strcpy(lTableName, PhxInfo.TableName);
    strcpy(lColumnName, PhxInfo.ColumnName);


    *Type = PhxInfo.PhnxDataType;
    // max len
    *MaxLen = PhxInfo.MaxDataLen;
    *Endorsement = PhxInfo.Endorsement;
    strcpy(EndorsementID, PhxInfo.EndorsementID);
    // determine which table we need the iteration of
    *lIteration = PhxIterationArray[PhxInfo.sEffectiveTableID];

    return SUCCESS;
}

Hier ist der C # -Code, der in den nicht verwalteten Code aufruft:

public int PhxQueryDataAttributes(int handle, ref string lTableName, ref string lColumnName, 
            ref short lIteration, ref short type, ref short maxLen, ref short endorsement, 
            ref string endorsementId)
        {
            var sbTableName = new StringBuilder();
            var sbColName = new StringBuilder();
            var sbEndId = new StringBuilder();

            var ret = RatingProxy.PhxQueryDataAttributes(handle, sbTableName, sbColName,
            ref lIteration, ref type, ref maxLen, ref endorsement, sbEndId);


            lTableName = sbTableName.ToString();
            lColumnName = sbColName.ToString();
            endorsementId = sbEndId.ToString();
return ret;
}

Danke, Corey

War es hilfreich?

Lösung 3

Nachdem ich die ersten 2 Antworten ausprobiert und gelernt, dass sie nicht halfen, wusste ich, dass etwas anderes vermuten sein muss. Ich fand einen kleinen Fehler irgendwo anders in meiner app, wo ich war eigentlich eine Initialisierung param auf dem nicht verwalteten Code fehlt. Dies wurde meine seltsam codierte Zeichenfolge verursacht.

Danke für die Hilfe, Corey

Andere Tipps

Ok, ich sehe Ihr Problem. Sie müssen über eine Kapazität für die StringBuilder zuzuteilen, man kann nicht nur die Standardeinstellung verwenden.

Statt der String, Sie könnten versuchen, einen IntPtr und die Marshal-Klasse.

SO, es würde wie folgt aussehen:

[DllImport("dmphnx32.dll")]
    public static extern int PhxQueryDataAttributes(int handle,
                                    IntPtr lTableName,
                                    IntPtr  lColumnName,
                                    ref short lIteration,
                                    ref short type,
                                    ref short maxLen,
                                    ref short endorsement,
                                    IntPtr endorsementId);

Telefonvorwahl wäre:

public int PhxQueryDataAttributes(int handle, ref string lTableName, ref string lColumnName, 
        ref short lIteration, ref short type, ref short maxLen, ref short endorsement, 
        ref string endorsementId)
    {
        var sbTableName = Marshal.AllocHGlobal(1024);//Change these to the max length possible for each string.
        var sbColName = Marshal.AllocHGlobal(1024);
        var sbEndId = = Marshal.AllocHGlobal(1024);

        var ret = RatingProxy.PhxQueryDataAttributes(handle, sbTableName, sbColName,
        ref lIteration, ref type, ref maxLen, ref endorsement, sbEndId);


        lTableName = Marshal.PtrToStringAnsi(sbTableName);
        lColumnName = Marshal.PtrToStringAnsi(sbColName);
        endorsementId = Marshal.PtrToStringAnsi(sbEndId);
        return ret;
}

So können Sie die richtige Codierung angeben (die Sie nicht mit einem String-Builder tun können, was es ist eine UTF-Typ-Codierung übernimmt). Experimentieren Sie ein wenig, und sehen, welche der Marshal.PtrToString ... diejenigen arbeiten, obwohl ANSI funktionieren sollte, denn das ist, was die meisten C ++ Bibliotheken.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top