diff options
343 files changed, 4752 insertions, 1577 deletions
diff --git a/fontconfig/doc/fontconfig-devel.sgml b/fontconfig/doc/fontconfig-devel.sgml index e2cb1c281..2b1122f18 100644 --- a/fontconfig/doc/fontconfig-devel.sgml +++ b/fontconfig/doc/fontconfig-devel.sgml @@ -198,7 +198,7 @@ convenience for the application's rendering mechanism. stylelang and fullnamelang prgname FC_PRGNAME String Name of the running program hash FC_HASH String SHA256 hash value of the font data - with "sha256:" prefix. + with "sha256:" prefix (deprecated) postscriptname FC_POSTSCRIPT_NAME String Font name in PostScript </programlisting> </sect2> diff --git a/fontconfig/fc-cache/fc-cache.c b/fontconfig/fc-cache/fc-cache.c index 90ebad32f..406ac6a8a 100644 --- a/fontconfig/fc-cache/fc-cache.c +++ b/fontconfig/fc-cache/fc-cache.c @@ -128,7 +128,8 @@ scanDirs (FcStrList *list, FcConfig *config, FcBool force, FcBool really_force, struct stat statb; FcBool was_valid; int i; - + const FcChar8 *sysroot = FcConfigGetSysRoot (config); + /* * Now scan all of the directories into separate databases * and write out the results @@ -138,9 +139,10 @@ scanDirs (FcStrList *list, FcConfig *config, FcBool force, FcBool really_force, if (verbose) { if (!recursive) - printf ("Re-scanning %s: ", dir); - else - printf ("%s: ", dir); + printf ("Re-scanning "); + if (sysroot) + printf ("[%s]", sysroot); + printf ("%s: ", dir); fflush (stdout); } diff --git a/fontconfig/fc-case/CaseFolding.txt b/fontconfig/fc-case/CaseFolding.txt index cf5779f40..13c10a6c4 100644 --- a/fontconfig/fc-case/CaseFolding.txt +++ b/fontconfig/fc-case/CaseFolding.txt @@ -1,8 +1,8 @@ -# CaseFolding-6.3.0.txt -# Date: 2012-12-20, 22:14:35 GMT [MD] +# CaseFolding-7.0.0.txt +# Date: 2014-04-09, 20:00:56 GMT [MD] # # Unicode Character Database -# Copyright (c) 1991-2013 Unicode, Inc. +# Copyright (c) 1991-2014 Unicode, Inc. # For terms of use, see http://www.unicode.org/terms_of_use.html # For documentation, see http://www.unicode.org/reports/tr44/ # @@ -25,7 +25,7 @@ # # For information on case folding, including how to have case folding # preserve normalization formats, see Section 3.13 Default Case Algorithms in -# The Unicode Standard, Version 5.0. +# The Unicode Standard. # # ================================================================================ # Format @@ -58,8 +58,6 @@ # All code points not explicitly listed for Case_Folding # have the value C for the status field, and the code point itself for the mapping field. -# @missing: 0000..10FFFF; C; <code point> - # ================================================================= 0041; C; 0061; # LATIN CAPITAL LETTER A 0042; C; 0062; # LATIN CAPITAL LETTER B @@ -298,6 +296,7 @@ 0370; C; 0371; # GREEK CAPITAL LETTER HETA 0372; C; 0373; # GREEK CAPITAL LETTER ARCHAIC SAMPI 0376; C; 0377; # GREEK CAPITAL LETTER PAMPHYLIAN DIGAMMA +037F; C; 03F3; # GREEK CAPITAL LETTER YOT 0386; C; 03AC; # GREEK CAPITAL LETTER ALPHA WITH TONOS 0388; C; 03AD; # GREEK CAPITAL LETTER EPSILON WITH TONOS 0389; C; 03AE; # GREEK CAPITAL LETTER ETA WITH TONOS @@ -505,6 +504,10 @@ 0522; C; 0523; # CYRILLIC CAPITAL LETTER EN WITH MIDDLE HOOK 0524; C; 0525; # CYRILLIC CAPITAL LETTER PE WITH DESCENDER 0526; C; 0527; # CYRILLIC CAPITAL LETTER SHHA WITH DESCENDER +0528; C; 0529; # CYRILLIC CAPITAL LETTER EN WITH LEFT HOOK +052A; C; 052B; # CYRILLIC CAPITAL LETTER DZZHE +052C; C; 052D; # CYRILLIC CAPITAL LETTER DCHE +052E; C; 052F; # CYRILLIC CAPITAL LETTER EL WITH DESCENDER 0531; C; 0561; # ARMENIAN CAPITAL LETTER AYB 0532; C; 0562; # ARMENIAN CAPITAL LETTER BEN 0533; C; 0563; # ARMENIAN CAPITAL LETTER GIM @@ -1088,6 +1091,8 @@ A690; C; A691; # CYRILLIC CAPITAL LETTER TSSE A692; C; A693; # CYRILLIC CAPITAL LETTER TCHE A694; C; A695; # CYRILLIC CAPITAL LETTER HWE A696; C; A697; # CYRILLIC CAPITAL LETTER SHWE +A698; C; A699; # CYRILLIC CAPITAL LETTER DOUBLE O +A69A; C; A69B; # CYRILLIC CAPITAL LETTER CROSSED O A722; C; A723; # LATIN CAPITAL LETTER EGYPTOLOGICAL ALEF A724; C; A725; # LATIN CAPITAL LETTER EGYPTOLOGICAL AIN A726; C; A727; # LATIN CAPITAL LETTER HENG @@ -1138,12 +1143,22 @@ A78B; C; A78C; # LATIN CAPITAL LETTER SALTILLO A78D; C; 0265; # LATIN CAPITAL LETTER TURNED H A790; C; A791; # LATIN CAPITAL LETTER N WITH DESCENDER A792; C; A793; # LATIN CAPITAL LETTER C WITH BAR +A796; C; A797; # LATIN CAPITAL LETTER B WITH FLOURISH +A798; C; A799; # LATIN CAPITAL LETTER F WITH STROKE +A79A; C; A79B; # LATIN CAPITAL LETTER VOLAPUK AE +A79C; C; A79D; # LATIN CAPITAL LETTER VOLAPUK OE +A79E; C; A79F; # LATIN CAPITAL LETTER VOLAPUK UE A7A0; C; A7A1; # LATIN CAPITAL LETTER G WITH OBLIQUE STROKE A7A2; C; A7A3; # LATIN CAPITAL LETTER K WITH OBLIQUE STROKE A7A4; C; A7A5; # LATIN CAPITAL LETTER N WITH OBLIQUE STROKE A7A6; C; A7A7; # LATIN CAPITAL LETTER R WITH OBLIQUE STROKE A7A8; C; A7A9; # LATIN CAPITAL LETTER S WITH OBLIQUE STROKE A7AA; C; 0266; # LATIN CAPITAL LETTER H WITH HOOK +A7AB; C; 025C; # LATIN CAPITAL LETTER REVERSED OPEN E +A7AC; C; 0261; # LATIN CAPITAL LETTER SCRIPT G +A7AD; C; 026C; # LATIN CAPITAL LETTER L WITH BELT +A7B0; C; 029E; # LATIN CAPITAL LETTER TURNED K +A7B1; C; 0287; # LATIN CAPITAL LETTER TURNED T FB00; F; 0066 0066; # LATIN SMALL LIGATURE FF FB01; F; 0066 0069; # LATIN SMALL LIGATURE FI FB02; F; 0066 006C; # LATIN SMALL LIGATURE FL @@ -1222,5 +1237,37 @@ FF3A; C; FF5A; # FULLWIDTH LATIN CAPITAL LETTER Z 10425; C; 1044D; # DESERET CAPITAL LETTER ENG 10426; C; 1044E; # DESERET CAPITAL LETTER OI 10427; C; 1044F; # DESERET CAPITAL LETTER EW +118A0; C; 118C0; # WARANG CITI CAPITAL LETTER NGAA +118A1; C; 118C1; # WARANG CITI CAPITAL LETTER A +118A2; C; 118C2; # WARANG CITI CAPITAL LETTER WI +118A3; C; 118C3; # WARANG CITI CAPITAL LETTER YU +118A4; C; 118C4; # WARANG CITI CAPITAL LETTER YA +118A5; C; 118C5; # WARANG CITI CAPITAL LETTER YO +118A6; C; 118C6; # WARANG CITI CAPITAL LETTER II +118A7; C; 118C7; # WARANG CITI CAPITAL LETTER UU +118A8; C; 118C8; # WARANG CITI CAPITAL LETTER E +118A9; C; 118C9; # WARANG CITI CAPITAL LETTER O +118AA; C; 118CA; # WARANG CITI CAPITAL LETTER ANG +118AB; C; 118CB; # WARANG CITI CAPITAL LETTER GA +118AC; C; 118CC; # WARANG CITI CAPITAL LETTER KO +118AD; C; 118CD; # WARANG CITI CAPITAL LETTER ENY +118AE; C; 118CE; # WARANG CITI CAPITAL LETTER YUJ +118AF; C; 118CF; # WARANG CITI CAPITAL LETTER UC +118B0; C; 118D0; # WARANG CITI CAPITAL LETTER ENN +118B1; C; 118D1; # WARANG CITI CAPITAL LETTER ODD +118B2; C; 118D2; # WARANG CITI CAPITAL LETTER TTE +118B3; C; 118D3; # WARANG CITI CAPITAL LETTER NUNG +118B4; C; 118D4; # WARANG CITI CAPITAL LETTER DA +118B5; C; 118D5; # WARANG CITI CAPITAL LETTER AT +118B6; C; 118D6; # WARANG CITI CAPITAL LETTER AM +118B7; C; 118D7; # WARANG CITI CAPITAL LETTER BU +118B8; C; 118D8; # WARANG CITI CAPITAL LETTER PU +118B9; C; 118D9; # WARANG CITI CAPITAL LETTER HIYO +118BA; C; 118DA; # WARANG CITI CAPITAL LETTER HOLO +118BB; C; 118DB; # WARANG CITI CAPITAL LETTER HORR +118BC; C; 118DC; # WARANG CITI CAPITAL LETTER HAR +118BD; C; 118DD; # WARANG CITI CAPITAL LETTER SSUU +118BE; C; 118DE; # WARANG CITI CAPITAL LETTER SII +118BF; C; 118DF; # WARANG CITI CAPITAL LETTER VIYO # # EOF diff --git a/fontconfig/fc-lang/ko.orth b/fontconfig/fc-lang/ko.orth index 39114a5af..4bb52c6f4 100644 --- a/fontconfig/fc-lang/ko.orth +++ b/fontconfig/fc-lang/ko.orth @@ -86,7 +86,6 @@ 0x3161 # HANGUL LETTER EU 0x3162 # HANGUL LETTER YI 0x3163 # HANGUL LETTER I -0x3164 # HANGUL FILLER 0x3165 # HANGUL LETTER SSANGNIEUN 0x3166 # HANGUL LETTER NIEUN-TIKEUT 0x3167 # HANGUL LETTER NIEUN-SIOS diff --git a/fontconfig/fontconfig/fontconfig.h b/fontconfig/fontconfig/fontconfig.h index 069cb60dd..8575cc4d3 100644 --- a/fontconfig/fontconfig/fontconfig.h +++ b/fontconfig/fontconfig/fontconfig.h @@ -115,7 +115,7 @@ typedef int FcBool; #define FC_FONT_FEATURES "fontfeatures" /* String */ #define FC_NAMELANG "namelang" /* String RFC 3866 langs */ #define FC_PRGNAME "prgname" /* String */ -#define FC_HASH "hash" /* String */ +#define FC_HASH "hash" /* String (deprecated) */ #define FC_POSTSCRIPT_NAME "postscriptname" /* String */ #define FC_CACHE_SUFFIX ".cache-" FC_CACHE_VERSION diff --git a/fontconfig/fonts.conf.in b/fontconfig/fonts.conf.in index 6a8753d01..f63ada1cd 100644 --- a/fontconfig/fonts.conf.in +++ b/fontconfig/fonts.conf.in @@ -88,17 +88,15 @@ <int>0x00A0</int> <!-- NO-BREAK SPACE --> <int>0x00AD</int> <!-- SOFT HYPHEN --> <int>0x034F</int> <!-- COMBINING GRAPHEME JOINER --> - <int>0x0600</int> <!-- ARABIC NUMBER SIGN --> - <int>0x0601</int> <!-- ARABIC SIGN SANAH --> - <int>0x0602</int> <!-- ARABIC FOOTNOTE MARKER --> - <int>0x0603</int> <!-- ARABIC SIGN SAFHA --> - <int>0x06DD</int> <!-- ARABIC END OF AYAH --> - <int>0x070F</int> <!-- SYRIAC ABBREVIATION MARK --> + <int>0x061C</int> <!-- ARABIC LETTER MARK --> <int>0x115F</int> <!-- HANGUL CHOSEONG FILLER --> <int>0x1160</int> <!-- HANGUL JUNGSEONG FILLER --> <int>0x1680</int> <!-- OGHAM SPACE MARK --> <int>0x17B4</int> <!-- KHMER VOWEL INHERENT AQ --> <int>0x17B5</int> <!-- KHMER VOWEL INHERENT AA --> + <int>0x180B</int> <!-- MONGOLIAN FREE VARIATION SELECTOR ONE --> + <int>0x180C</int> <!-- MONGOLIAN FREE VARIATION SELECTOR TWO --> + <int>0x180D</int> <!-- MONGOLIAN FREE VARIATION SELECTOR THREE --> <int>0x180E</int> <!-- MONGOLIAN VOWEL SEPARATOR --> <int>0x2000</int> <!-- EN QUAD --> <int>0x2001</int> <!-- EM QUAD --> @@ -116,8 +114,6 @@ <int>0x200D</int> <!-- ZERO WIDTH JOINER --> <int>0x200E</int> <!-- LEFT-TO-RIGHT MARK --> <int>0x200F</int> <!-- RIGHT-TO-LEFT MARK --> - <int>0x2028</int> <!-- LINE SEPARATOR --> - <int>0x2029</int> <!-- PARAGRAPH SEPARATOR --> <int>0x202A</int> <!-- LEFT-TO-RIGHT EMBEDDING --> <int>0x202B</int> <!-- RIGHT-TO-LEFT EMBEDDING --> <int>0x202C</int> <!-- POP DIRECTIONAL FORMATTING --> @@ -129,6 +125,11 @@ <int>0x2061</int> <!-- FUNCTION APPLICATION --> <int>0x2062</int> <!-- INVISIBLE TIMES --> <int>0x2063</int> <!-- INVISIBLE SEPARATOR --> + <int>0x2064</int> <!-- INVISIBLE PLUS --> + <int>0x2066</int> <!-- LEFT-TO-RIGHT ISOLATE --> + <int>0x2067</int> <!-- RIGHT-TO-LEFT ISOLATE --> + <int>0x2068</int> <!-- FIRST STRONG ISOLATE --> + <int>0x2069</int> <!-- POP DIRECTIONAL ISOLATE --> <int>0x206A</int> <!-- INHIBIT SYMMETRIC SWAPPING --> <int>0x206B</int> <!-- ACTIVATE SYMMETRIC SWAPPING --> <int>0x206C</int> <!-- INHIBIT ARABIC FORM SHAPING --> @@ -140,9 +141,10 @@ <int>0x3164</int> <!-- HANGUL FILLER --> <int>0xFEFF</int> <!-- ZERO WIDTH NO-BREAK SPACE --> <int>0xFFA0</int> <!-- HALFWIDTH HANGUL FILLER --> - <int>0xFFF9</int> <!-- INTERLINEAR ANNOTATION ANCHOR --> - <int>0xFFFA</int> <!-- INTERLINEAR ANNOTATION SEPARATOR --> - <int>0xFFFB</int> <!-- INTERLINEAR ANNOTATION TERMINATOR --> + <int>0x1BCA0</int> <!-- SHORTHAND FORMAT LETTER OVERLAP --> + <int>0x1BCA1</int> <!-- SHORTHAND FORMAT CONTINUING OVERLAP --> + <int>0x1BCA2</int> <!-- SHORTHAND FORMAT DOWN STEP --> + <int>0x1BCA3</int> <!-- SHORTHAND FORMAT UP STEP --> </blank> <!-- Rescan configuration every 30 seconds when FcFontSetList is called diff --git a/fontconfig/src/Makefile.am b/fontconfig/src/Makefile.am index be20eba05..c1991b284 100644 --- a/fontconfig/src/Makefile.am +++ b/fontconfig/src/Makefile.am @@ -139,7 +139,6 @@ libfontconfig_la_SOURCES = \ fcformat.c \ fcfreetype.c \ fcfs.c \ - fchash.c \ fcinit.c \ fclang.c \ fclist.c \ diff --git a/fontconfig/src/fccache.c b/fontconfig/src/fccache.c index 085bd72e3..25538bd70 100644 --- a/fontconfig/src/fccache.c +++ b/fontconfig/src/fccache.c @@ -177,19 +177,28 @@ FcDirCacheOpenFile (const FcChar8 *cache_file, struct stat *file_stat) */ static FcBool FcDirCacheProcess (FcConfig *config, const FcChar8 *dir, - FcBool (*callback) (int fd, struct stat *fd_stat, + FcBool (*callback) (FcConfig *config, int fd, struct stat *fd_stat, struct stat *dir_stat, void *closure), void *closure, FcChar8 **cache_file_ret) { int fd = -1; FcChar8 cache_base[CACHEBASE_LEN]; FcStrList *list; - FcChar8 *cache_dir; + FcChar8 *cache_dir, *d; struct stat file_stat, dir_stat; FcBool ret = FcFalse; + const FcChar8 *sysroot = FcConfigGetSysRoot (config); - if (FcStatChecksum (dir, &dir_stat) < 0) + if (sysroot) + d = FcStrBuildFilename (sysroot, dir, NULL); + else + d = FcStrdup (dir); + if (FcStatChecksum (d, &dir_stat) < 0) + { + FcStrFree (d); return FcFalse; + } + FcStrFree (d); FcDirCacheBasename (dir, cache_base); @@ -199,7 +208,6 @@ FcDirCacheProcess (FcConfig *config, const FcChar8 *dir, while ((cache_dir = FcStrListNext (list))) { - const FcChar8 *sysroot = FcConfigGetSysRoot (config); FcChar8 *cache_hashed; if (sysroot) @@ -210,7 +218,7 @@ FcDirCacheProcess (FcConfig *config, const FcChar8 *dir, break; fd = FcDirCacheOpenFile (cache_hashed, &file_stat); if (fd >= 0) { - ret = (*callback) (fd, &file_stat, &dir_stat, closure); + ret = (*callback) (config, fd, &file_stat, &dir_stat, closure); close (fd); if (ret) { @@ -529,14 +537,25 @@ FcCacheFini (void) } static FcBool -FcCacheTimeValid (FcCache *cache, struct stat *dir_stat) +FcCacheTimeValid (FcConfig *config, FcCache *cache, struct stat *dir_stat) { struct stat dir_static; if (!dir_stat) { - if (FcStatChecksum (FcCacheDir (cache), &dir_static) < 0) + const FcChar8 *sysroot = FcConfigGetSysRoot (config); + FcChar8 *d; + + if (sysroot) + d = FcStrBuildFilename (sysroot, FcCacheDir (cache), NULL); + else + d = FcStrdup (FcCacheDir (cache)); + if (FcStatChecksum (d, &dir_static) < 0) + { + FcStrFree (d); return FcFalse; + } + FcStrFree (d); dir_stat = &dir_static; } if (FcDebug () & FC_DBG_CACHE) @@ -546,21 +565,28 @@ FcCacheTimeValid (FcCache *cache, struct stat *dir_stat) } static FcBool -FcCacheDirsValid (FcCache *cache) +FcCacheDirsValid (FcConfig *config, FcCache *cache) { FcStrSet *dirs = FcStrSetCreate (); FcBool ret = FcFalse; + const FcChar8 *sysroot = FcConfigGetSysRoot (config); + FcChar8 *d; if (!dirs) goto bail; - if (!FcDirScanOnly (dirs, FcCacheDir (cache))) + if (sysroot) + d = FcStrBuildFilename (sysroot, FcCacheDir (cache), NULL); + else + d = FcStrdup (FcCacheDir (cache)); + if (!FcDirScanOnly (dirs, d, config)) goto bail1; ret = cache->dirs_count == dirs->num; if (FcDebug () & FC_DBG_CACHE) - printf ("%s: cache: %d, fs: %d\n", FcCacheDir (cache), cache->dirs_count, dirs->num); + printf ("%s: cache: %d, fs: %d\n", d, cache->dirs_count, dirs->num); bail1: FcStrSetDestroy (dirs); + FcStrFree (d); bail: return ret; } @@ -569,7 +595,7 @@ bail: * Map a cache file into memory */ static FcCache * -FcDirCacheMapFd (int fd, struct stat *fd_stat, struct stat *dir_stat) +FcDirCacheMapFd (FcConfig *config, int fd, struct stat *fd_stat, struct stat *dir_stat) { FcCache *cache; FcBool allocated = FcFalse; @@ -579,8 +605,8 @@ FcDirCacheMapFd (int fd, struct stat *fd_stat, struct stat *dir_stat) cache = FcCacheFindByStat (fd_stat); if (cache) { - if (FcCacheTimeValid (cache, dir_stat) && - FcCacheDirsValid (cache)) + if (FcCacheTimeValid (config, cache, dir_stat) && + FcCacheDirsValid (config, cache)) return cache; FcDirCacheUnload (cache); cache = NULL; @@ -631,8 +657,8 @@ FcDirCacheMapFd (int fd, struct stat *fd_stat, struct stat *dir_stat) if (cache->magic != FC_CACHE_MAGIC_MMAP || cache->version < FC_CACHE_CONTENT_VERSION || cache->size != (intptr_t) fd_stat->st_size || - !FcCacheTimeValid (cache, dir_stat) || - !FcCacheDirsValid (cache) || + !FcCacheTimeValid (config, cache, dir_stat) || + !FcCacheDirsValid (config, cache) || !FcCacheInsert (cache, fd_stat)) { if (allocated) @@ -671,9 +697,9 @@ FcDirCacheUnload (FcCache *cache) } static FcBool -FcDirCacheMapHelper (int fd, struct stat *fd_stat, struct stat *dir_stat, void *closure) +FcDirCacheMapHelper (FcConfig *config, int fd, struct stat *fd_stat, struct stat *dir_stat, void *closure) { - FcCache *cache = FcDirCacheMapFd (fd, fd_stat, dir_stat); + FcCache *cache = FcDirCacheMapFd (config, fd, fd_stat, dir_stat); if (!cache) return FcFalse; @@ -690,6 +716,7 @@ FcDirCacheLoad (const FcChar8 *dir, FcConfig *config, FcChar8 **cache_file) FcDirCacheMapHelper, &cache, cache_file)) return NULL; + return cache; } @@ -705,7 +732,7 @@ FcDirCacheLoadFile (const FcChar8 *cache_file, struct stat *file_stat) fd = FcDirCacheOpenFile (cache_file, file_stat); if (fd < 0) return NULL; - cache = FcDirCacheMapFd (fd, file_stat, NULL); + cache = FcDirCacheMapFd (FcConfigGetCurrent (), fd, file_stat, NULL); close (fd); return cache; } @@ -715,7 +742,7 @@ FcDirCacheLoadFile (const FcChar8 *cache_file, struct stat *file_stat) * the magic number and the size field */ static FcBool -FcDirCacheValidateHelper (int fd, struct stat *fd_stat, struct stat *dir_stat, void *closure FC_UNUSED) +FcDirCacheValidateHelper (FcConfig *config, int fd, struct stat *fd_stat, struct stat *dir_stat, void *closure FC_UNUSED) { FcBool ret = FcTrue; FcCache c; @@ -1080,15 +1107,22 @@ FcDirCacheClean (const FcChar8 *cache_dir, FcBool verbose) } else { + FcChar8 *s; + target_dir = FcCacheDir (cache); - if (stat ((char *) target_dir, &target_stat) < 0) + if (sysroot) + s = FcStrBuildFilename (sysroot, target_dir, NULL); + else + s = FcStrdup (target_dir); + if (stat ((char *) s, &target_stat) < 0) { if (verbose || FcDebug () & FC_DBG_CACHE) printf ("%s: %s: missing directory: %s \n", - dir, ent->d_name, target_dir); + dir, ent->d_name, s); remove = FcTrue; } FcDirCacheUnload (cache); + FcStrFree (s); } if (remove) { diff --git a/fontconfig/src/fccfg.c b/fontconfig/src/fccfg.c index fe69eecd7..8b62e520c 100644 --- a/fontconfig/src/fccfg.c +++ b/fontconfig/src/fccfg.c @@ -375,7 +375,7 @@ FcConfigAddDirList (FcConfig *config, FcSetName set, FcStrSet *dirSet) while ((dir = FcStrListNext (dirlist))) { if (FcDebug () & FC_DBG_FONTSET) - printf ("adding fonts from%s\n", dir); + printf ("adding fonts from %s\n", dir); cache = FcDirCacheRead (dir, FcFalse, config); if (!cache) continue; diff --git a/fontconfig/src/fcdir.c b/fontconfig/src/fcdir.c index 49259c1f2..593382f43 100644 --- a/fontconfig/src/fcdir.c +++ b/fontconfig/src/fcdir.c @@ -69,6 +69,7 @@ FcFileScanFontConfig (FcFontSet *set, FcBool ret = FcTrue; int id; int count = 0; + const FcChar8 *sysroot = FcConfigGetSysRoot (config); id = 0; do @@ -85,6 +86,28 @@ FcFileScanFontConfig (FcFontSet *set, font = FcFreeTypeQuery (file, id, blanks, &count); if (FcDebug () & FC_DBG_SCAN) printf ("done\n"); + /* + * Get rid of sysroot here so that targeting scan rule may contains FC_FILE pattern + * and they should usually expect without sysroot. + */ + if (sysroot) + { + size_t len = strlen ((const char *)sysroot); + FcChar8 *f = NULL; + + if (FcPatternObjectGetString (font, FC_FILE_OBJECT, 0, &f) == FcResultMatch && + strncmp ((const char *)f, (const char *)sysroot, len) == 0) + { + FcChar8 *s = FcStrdup (f); + FcPatternObjectDel (font, FC_FILE_OBJECT); + if (s[len] != '/') + len--; + else if (s[len+1] == '/') + len++; + FcPatternObjectAddString (font, FC_FILE_OBJECT, &s[len]); + FcStrFree (s); + } + } /* * Edit pattern with user-defined rules @@ -128,7 +151,25 @@ FcFileScanConfig (FcFontSet *set, FcConfig *config) { if (FcFileIsDir (file)) - return FcStrSetAdd (dirs, file); + { + const FcChar8 *sysroot = FcConfigGetSysRoot (config); + const FcChar8 *d = file; + size_t len; + + if (sysroot) + { + len = strlen ((const char *)sysroot); + if (strncmp ((const char *)file, (const char *)sysroot, len) == 0) + { + if (file[len] != '/') + len--; + else if (file[len+1] == '/') + len++; + d = &file[len]; + } + } + return FcStrSetAdd (dirs, d); + } else { if (set) @@ -238,7 +279,7 @@ FcDirScanConfig (FcFontSet *set, if (scanOnly) { if (FcFileIsDir (files->strs[i])) - FcStrSetAdd (dirs, files->strs[i]); + FcFileScanConfig (NULL, dirs, NULL, files->strs[i], config); } else { @@ -273,9 +314,10 @@ FcDirScan (FcFontSet *set, FcBool FcDirScanOnly (FcStrSet *dirs, - const FcChar8 *dir) + const FcChar8 *dir, + FcConfig *config) { - return FcDirScanConfig (NULL, dirs, NULL, dir, FcTrue, NULL, FcTrue); + return FcDirScanConfig (NULL, dirs, NULL, dir, FcTrue, config, FcTrue); } /* @@ -288,11 +330,18 @@ FcDirCacheScan (const FcChar8 *dir, FcConfig *config) FcFontSet *set; FcCache *cache = NULL; struct stat dir_stat; + const FcChar8 *sysroot = FcConfigGetSysRoot (config); + FcChar8 *d; + + if (sysroot) + d = FcStrBuildFilename (sysroot, dir, NULL); + else + d = FcStrdup (dir); if (FcDebug () & FC_DBG_FONTSET) - printf ("cache scan dir %s\n", dir); + printf ("cache scan dir %s\n", d); - if (FcStatChecksum (dir, &dir_stat) < 0) + if (FcStatChecksum (d, &dir_stat) < 0) goto bail; set = FcFontSetCreate(); @@ -306,7 +355,7 @@ FcDirCacheScan (const FcChar8 *dir, FcConfig *config) /* * Scan the dir */ - if (!FcDirScanConfig (set, dirs, NULL, dir, FcTrue, config, FcFalse)) + if (!FcDirScanConfig (set, dirs, NULL, d, FcTrue, config, FcFalse)) goto bail2; /* @@ -326,20 +375,30 @@ FcDirCacheScan (const FcChar8 *dir, FcConfig *config) bail1: FcFontSetDestroy (set); bail: + FcStrFree (d); + return cache; } FcCache * FcDirCacheRescan (const FcChar8 *dir, FcConfig *config) { - FcCache *cache = FcDirCacheLoad (dir, config, NULL); + FcCache *cache; FcCache *new = NULL; struct stat dir_stat; FcStrSet *dirs; + const FcChar8 *sysroot = FcConfigGetSysRoot (config); + FcChar8 *d = NULL; + cache = FcDirCacheLoad (dir, config, NULL); if (!cache) - return NULL; - if (FcStatChecksum (dir, &dir_stat) < 0) + goto bail; + + if (sysroot) + d = FcStrBuildFilename (sysroot, dir, NULL); + else + d = FcStrdup (dir); + if (FcStatChecksum (d, &dir_stat) < 0) goto bail; dirs = FcStrSetCreate (); if (!dirs) @@ -348,7 +407,7 @@ FcDirCacheRescan (const FcChar8 *dir, FcConfig *config) /* * Scan the dir */ - if (!FcDirScanConfig (NULL, dirs, NULL, dir, FcTrue, config, FcFalse)) + if (!FcDirScanConfig (NULL, dirs, NULL, d, FcTrue, config, FcFalse)) goto bail1; /* * Rebuild the cache object @@ -365,6 +424,9 @@ FcDirCacheRescan (const FcChar8 *dir, FcConfig *config) bail1: FcStrSetDestroy (dirs); bail: + if (d) + FcStrFree (d); + return new; } diff --git a/fontconfig/src/fcfreetype.c b/fontconfig/src/fcfreetype.c index ae19ae91b..3eb409160 100644 --- a/fontconfig/src/fcfreetype.c +++ b/fontconfig/src/fcfreetype.c @@ -1698,55 +1698,6 @@ FcFreeTypeQueryFace (const FT_Face face, /* - * Compute hash digest for the font - */ - { - FcChar8 *hashstr = NULL; - FcHashDigest digest; - - FcHashInitDigest (digest); - - if (face->stream->read == NULL) - { - const char *data = (const char *) face->stream->base; - size_t total_len = face->stream->size; - size_t len = total_len; - - while (len >= 64) - { - FcHashDigestAddBlock (digest, data); - data += 64; - len -= 64; - } - FcHashDigestFinish (digest, data, total_len); - } else { - char data[64]; - size_t total_len = 0; - size_t len = 0; - - while ((len = face->stream->read (face->stream, total_len, (unsigned char *) data, sizeof(data))) == 64) - { - FcHashDigestAddBlock (digest, data); - total_len += 64; - } - total_len += len; - FcHashDigestFinish (digest, data, total_len); - } - - hashstr = FcHashToString (digest); - if (hashstr) - { - if (!FcPatternAddString (pat, FC_HASH, hashstr)) - { - free (hashstr); - goto bail1; - } - free (hashstr); - } - } - - - /* * Compute the unicode coverage for the font */ cs = FcFreeTypeCharSetAndSpacing (face, blanks, &spacing); diff --git a/fontconfig/src/fchash.c b/fontconfig/src/fchash.c deleted file mode 100644 index 1526cfd2b..000000000 --- a/fontconfig/src/fchash.c +++ /dev/null @@ -1,189 +0,0 @@ -/* - * fontconfig/src/fchash.c - * - * Copyright © 2003 Keith Packard - * Copyright © 2013 Red Hat, Inc. - * Copyright © 2014 Google, Inc. - * Red Hat Author(s): Akira TAGOH - * Google Author(s): Behdad Esfahbod - * - * Permission to use, copy, modify, distribute, and sell this software and its - * documentation for any purpose is hereby granted without fee, provided that - * the above copyright notice appear in all copies and that both that - * copyright notice and this permission notice appear in supporting - * documentation, and that the name of the author(s) not be used in - * advertising or publicity pertaining to distribution of the software without - * specific, written prior permission. The authors make no - * representations about the suitability of this software for any purpose. It - * is provided "as is" without express or implied warranty. - * - * THE AUTHOR(S) DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, - * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO - * EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY SPECIAL, INDIRECT OR - * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, - * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER - * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR - * PERFORMANCE OF THIS SOFTWARE. - */ -#include "fcint.h" -#include <stdio.h> -#include <string.h> - -/* SHA256 */ - - -#define ROTRN(w, v, n) ((((FcChar32)v) >> n) | (((FcChar32)v) << (w - n))) -#define ROTR32(v, n) ROTRN(32, v, n) -#define SHR(v, n) (v >> n) -#define Ch(x, y, z) ((x & y) ^ (~x & z)) -#define Maj(x, y, z) ((x & y) ^ (x & z) ^ (y & z)) -#define SS0(x) (ROTR32(x, 2) ^ ROTR32(x, 13) ^ ROTR32(x, 22)) -#define SS1(x) (ROTR32(x, 6) ^ ROTR32(x, 11) ^ ROTR32(x, 25)) -#define ss0(x) (ROTR32(x, 7) ^ ROTR32(x, 18) ^ SHR(x, 3)) -#define ss1(x) (ROTR32(x, 17) ^ ROTR32(x, 19) ^ SHR(x, 10)) - - - -void -FcHashInitDigest (FcHashDigest digest) -{ - static const FcHashDigest init = { - 0x6a09e667UL, 0xbb67ae85UL, 0x3c6ef372UL, 0xa54ff53aUL, - 0x510e527fUL, 0x9b05688cUL, 0x1f83d9abUL, 0x5be0cd19UL - }; - - memcpy (digest, init, sizeof (FcHashDigest)); -} - -void -FcHashDigestAddBlock (FcHashDigest digest, - const char block[64]) -{ - static const FcChar32 k[] = { - 0x428a2f98UL, 0x71374491UL, 0xb5c0fbcfUL, 0xe9b5dba5UL, - 0x3956c25bUL, 0x59f111f1UL, 0x923f82a4UL, 0xab1c5ed5UL, - 0xd807aa98UL, 0x12835b01UL, 0x243185beUL, 0x550c7dc3UL, - 0x72be5d74UL, 0x80deb1feUL, 0x9bdc06a7UL, 0xc19bf174UL, - 0xe49b69c1UL, 0xefbe4786UL, 0x0fc19dc6UL, 0x240ca1ccUL, - 0x2de92c6fUL, 0x4a7484aaUL, 0x5cb0a9dcUL, 0x76f988daUL, - 0x983e5152UL, 0xa831c66dUL, 0xb00327c8UL, 0xbf597fc7UL, - 0xc6e00bf3UL, 0xd5a79147UL, 0x06ca6351UL, 0x14292967UL, - 0x27b70a85UL, 0x2e1b2138UL, 0x4d2c6dfcUL, 0x53380d13UL, - 0x650a7354UL, 0x766a0abbUL, 0x81c2c92eUL, 0x92722c85UL, - 0xa2bfe8a1UL, 0xa81a664bUL, 0xc24b8b70UL, 0xc76c51a3UL, - 0xd192e819UL, 0xd6990624UL, 0xf40e3585UL, 0x106aa070UL, - 0x19a4c116UL, 0x1e376c08UL, 0x2748774cUL, 0x34b0bcb5UL, - 0x391c0cb3UL, 0x4ed8aa4aUL, 0x5b9cca4fUL, 0x682e6ff3UL, - 0x748f82eeUL, 0x78a5636fUL, 0x84c87814UL, 0x8cc70208UL, - 0x90befffaUL, 0xa4506cebUL, 0xbef9a3f7UL, 0xc67178f2UL - }; - FcChar32 w[64], i, j, t1, t2; - FcChar32 a, b, c, d, e, f, g, h; - -#define H(n) (digest[n]) - - a = H(0); - b = H(1); - c = H(2); - d = H(3); - e = H(4); - f = H(5); - g = H(6); - h = H(7); - - for (i = 0; i < 16; i++) - { - j = (block[(i * 4) + 0] & 0xff) << (8 * 3); - j |= (block[(i * 4) + 1] & 0xff) << (8 * 2); - j |= (block[(i * 4) + 2] & 0xff) << (8 * 1); - j |= (block[(i * 4) + 3] & 0xff); - w[i] = j; - } - for (i = 16; i < 64; i++) - w[i] = ss1(w[i - 2]) + w[i - 7] + ss0(w[i - 15]) + w[i - 16]; - - for (i = 0; i < 64; i++) - { - t1 = h + SS1(e) + Ch(e, f, g) + k[i] + w[i]; - t2 = SS0(a) + Maj(a, b, c); - h = g; - g = f; - f = e; - e = d + t1; - d = c; - c = b; - b = a; - a = t1 + t2; - } - - H(0) += a; - H(1) += b; - H(2) += c; - H(3) += d; - H(4) += e; - H(5) += f; - H(6) += g; - H(7) += h; - -#undef H -} - -void -FcHashDigestFinish (FcHashDigest digest, - const char *residual, /* < 64 bytes */ - size_t total_len) -{ - char ibuf[64]; - unsigned int len = total_len % 64; - uint64_t v; - - if (!len) - return; - - memcpy (ibuf, residual, len); - memset (ibuf + len, 0, 64 - len); - ibuf[len] = 0x80; - - if ((64 - len) < 9) - { - FcHashDigestAddBlock (digest, ibuf); - memset (ibuf, 0, 64); - } - - /* set input size at the end */ - v = (uint64_t) total_len * 8; - ibuf[63 - 0] = v & 0xff; - ibuf[63 - 1] = (v >> 8) & 0xff; - ibuf[63 - 2] = (v >> 16) & 0xff; - ibuf[63 - 3] = (v >> 24) & 0xff; - ibuf[63 - 4] = (v >> 32) & 0xff; - ibuf[63 - 5] = (v >> 40) & 0xff; - ibuf[63 - 6] = (v >> 48) & 0xff; - ibuf[63 - 7] = (v >> 56) & 0xff; - FcHashDigestAddBlock (digest, ibuf); -} - -FcChar8 * -FcHashToString (const FcHashDigest digest) -{ - FcChar8 *ret = NULL; - static const char hex[] = "0123456789abcdef"; - int i, j; - - ret = malloc (sizeof (FcChar8) * (8 * 8 + 7 + 1)); - if (!ret) - return NULL; - memcpy (ret, "sha256:", 7); -#define H(n) digest[n] - for (i = 0; i < 8; i++) - { - FcChar32 v = H(i); - - for (j = 0; j < 8; j++) - ret[7 + (i * 8) + j] = hex[(v >> (28 - j * 4)) & 0xf]; - } - ret[7 + i * 8] = 0; -#undef H - - return ret; -} diff --git a/fontconfig/src/fcinit.c b/fontconfig/src/fcinit.c index b8d5d060c..1e23c1fbb 100644 --- a/fontconfig/src/fcinit.c +++ b/fontconfig/src/fcinit.c @@ -36,13 +36,14 @@ #endif static FcConfig * -FcInitFallbackConfig (void) +FcInitFallbackConfig (const FcChar8 *sysroot) { FcConfig *config; config = FcConfigCreate (); if (!config) goto bail0; + FcConfigSetSysRoot (config, sysroot); if (!FcConfigAddDir (config, (FcChar8 *) FC_DEFAULT_FONTS)) goto bail1; if (!FcConfigAddCacheDir (config, (FcChar8 *) FC_CACHEDIR)) @@ -78,8 +79,12 @@ FcInitLoadOwnConfig (FcConfig *config) if (!FcConfigParseAndLoad (config, 0, FcTrue)) { + const FcChar8 *sysroot = FcConfigGetSysRoot (config); + FcConfig *fallback = FcInitFallbackConfig (sysroot); + FcConfigDestroy (config); - return FcInitFallbackConfig (); + + return fallback; } if (config->cacheDirs && config->cacheDirs->num == 0) @@ -108,13 +113,19 @@ FcInitLoadOwnConfig (FcConfig *config) if (!FcConfigAddCacheDir (config, (FcChar8 *) FC_CACHEDIR) || !FcConfigAddCacheDir (config, (FcChar8 *) prefix)) { + FcConfig *fallback; + const FcChar8 *sysroot; + bail: + sysroot = FcConfigGetSysRoot (config); fprintf (stderr, "Fontconfig error: out of memory"); if (prefix) FcStrFree (prefix); + fallback = FcInitFallbackConfig (sysroot); FcConfigDestroy (config); - return FcInitFallbackConfig (); + + return fallback; } FcStrFree (prefix); } diff --git a/fontconfig/src/fcint.h b/fontconfig/src/fcint.h index a1b147f1d..d3079edcc 100644 --- a/fontconfig/src/fcint.h +++ b/fontconfig/src/fcint.h @@ -854,7 +854,8 @@ FcDirScanConfig (FcFontSet *set, FcPrivate FcBool FcDirScanOnly (FcStrSet *dirs, - const FcChar8 *dir); + const FcChar8 *dir, + FcConfig *config); /* fcfont.c */ FcPrivate int @@ -871,25 +872,6 @@ FcFontSetSerialize (FcSerialize *serialize, const FcFontSet * s); FcPrivate FcFontSet * FcFontSetDeserialize (const FcFontSet *set); -/* fchash.c */ - -typedef FcChar32 FcHashDigest[8]; - -FcPrivate void -FcHashInitDigest (FcHashDigest digest); - -FcPrivate void -FcHashDigestAddBlock (FcHashDigest digest, - const char block[64]); - -FcPrivate void -FcHashDigestFinish (FcHashDigest digest, - const char *residual, /* < 64 bytes */ - size_t total_len); - -FcPrivate FcChar8 * -FcHashToString (const FcHashDigest digest); - /* fcinit.c */ FcPrivate FcConfig * FcInitLoadOwnConfig (FcConfig *config); diff --git a/fontconfig/src/fcobjs.h b/fontconfig/src/fcobjs.h index 72e71f99c..dc3d83404 100644 --- a/fontconfig/src/fcobjs.h +++ b/fontconfig/src/fcobjs.h @@ -44,7 +44,7 @@ FC_OBJECT (AUTOHINT, FcTypeBool, NULL) FC_OBJECT (GLOBAL_ADVANCE, FcTypeBool, NULL) /* deprecated */ FC_OBJECT (FILE, FcTypeString, FcCompareFilename) FC_OBJECT (INDEX, FcTypeInteger, NULL) -FC_OBJECT (RASTERIZER, FcTypeString, FcCompareString) +FC_OBJECT (RASTERIZER, FcTypeString, FcCompareString) /* deprecated */ FC_OBJECT (OUTLINE, FcTypeBool, FcCompareBool) FC_OBJECT (SCALABLE, FcTypeBool, FcCompareBool) FC_OBJECT (DPI, FcTypeDouble, NULL) @@ -66,6 +66,6 @@ FC_OBJECT (LCD_FILTER, FcTypeInteger, NULL) FC_OBJECT (NAMELANG, FcTypeString, NULL) FC_OBJECT (FONT_FEATURES, FcTypeString, NULL) FC_OBJECT (PRGNAME, FcTypeString, NULL) -FC_OBJECT (HASH, FcTypeString, FcCompareHash) +FC_OBJECT (HASH, FcTypeString, FcCompareHash) /* deprecated */ FC_OBJECT (POSTSCRIPT_NAME, FcTypeString, FcComparePostScript) /* ^-------------- Add new objects here. */ diff --git a/fontconfig/src/fcxml.c b/fontconfig/src/fcxml.c index 9f4c2b062..e4c811cd5 100644 --- a/fontconfig/src/fcxml.c +++ b/fontconfig/src/fcxml.c @@ -3130,11 +3130,12 @@ FcConfigParseAndLoad (FcConfig *config, { XML_Parser p; - FcChar8 *filename; + FcChar8 *filename, *f; int fd; int len; FcConfigParse parse; FcBool error = FcTrue; + const FcChar8 *sysroot = FcConfigGetSysRoot (config); #ifdef ENABLE_LIBXML2 xmlSAXHandler sax; @@ -3159,9 +3160,14 @@ FcConfigParseAndLoad (FcConfig *config, } #endif - filename = FcConfigFilename (name); - if (!filename) + f = FcConfigFilename (name); + if (!f) goto bail0; + if (sysroot) + filename = FcStrBuildFilename (sysroot, f, NULL); + else + filename = FcStrdup (f); + FcStrFree (f); if (FcStrSetMember (config->configFiles, filename)) { diff --git a/libX11/src/GetHints.c b/libX11/src/GetHints.c index 513b4b090..f2e1d5676 100644 --- a/libX11/src/GetHints.c +++ b/libX11/src/GetHints.c @@ -258,7 +258,7 @@ Status XGetCommand ( return (0); } - if (tp.value) Xfree (tp.value); + Xfree (tp.value); *argvp = argv; *argcp = argc; return 1; diff --git a/libX11/src/GetWMProto.c b/libX11/src/GetWMProto.c index 4e9f12c22..cc1618d86 100644 --- a/libX11/src/GetWMProto.c +++ b/libX11/src/GetWMProto.c @@ -77,7 +77,7 @@ Status XGetWMProtocols ( return False; if (actual_type != XA_ATOM || actual_format != 32) { - if (data) Xfree (data); + Xfree (data); return False; } diff --git a/libX11/src/xkb/XKBAlloc.c b/libX11/src/xkb/XKBAlloc.c index 5cfef0fb8..50a5764d6 100644 --- a/libX11/src/xkb/XKBAlloc.c +++ b/libX11/src/xkb/XKBAlloc.c @@ -442,8 +442,7 @@ XkbAllocDeviceInfo(unsigned deviceSpec, unsigned nButtons, unsigned szLeds) devi->sz_leds = szLeds; devi->leds = _XkbTypedCalloc(szLeds, XkbDeviceLedInfoRec); if (!devi->leds) { - if (devi->btn_acts) - _XkbFree(devi->btn_acts); + _XkbFree(devi->btn_acts); _XkbFree(devi); return NULL; } diff --git a/libX11/src/xkb/XKBExtDev.c b/libX11/src/xkb/XKBExtDev.c index 4065dcd0e..b9710f86b 100644 --- a/libX11/src/xkb/XKBExtDev.c +++ b/libX11/src/xkb/XKBExtDev.c @@ -194,8 +194,8 @@ _XkbReadGetDeviceInfoReply(Display *dpy, act = &devi->btn_acts[rep->firstBtnWanted]; bzero((char *) act, (rep->nBtnsWanted * sizeof(XkbAction))); } - if (devi->name != NULL) - _XkbFree(devi->name); + + _XkbFree(devi->name); if (!_XkbGetReadBufferCountedString(&buf, &devi->name)) goto BAILOUT; if (rep->nBtnsRtrn > 0) { @@ -475,7 +475,7 @@ _InitLedStuff(SetLedStuff *stuff, unsigned wanted, XkbDeviceInfoPtr devi) static void _FreeLedStuff(SetLedStuff * stuff) { - if ((stuff->num_info > 0) && (stuff->info != NULL)) + if (stuff->num_info > 0) _XkbFree(stuff->info); bzero(stuff, sizeof(SetLedStuff)); return; diff --git a/libX11/src/xkb/XKBGAlloc.c b/libX11/src/xkb/XKBGAlloc.c index ecac4f33c..64d47f19b 100644 --- a/libX11/src/xkb/XKBGAlloc.c +++ b/libX11/src/xkb/XKBGAlloc.c @@ -179,8 +179,7 @@ _XkbClearColor(char *color_in) { XkbColorPtr color = (XkbColorPtr) color_in; - if (color->spec) - _XkbFree(color->spec); + _XkbFree(color->spec); return; } @@ -662,8 +661,7 @@ XkbAddGeomProperty(XkbGeometryPtr geom, char *name, char *value) return NULL; for (i = 0, prop = geom->properties; i < geom->num_properties; i++, prop++) { if ((prop->name) && (strcmp(name, prop->name) == 0)) { - if (prop->value) - _XkbFree(prop->value); + _XkbFree(prop->value); prop->value = strdup(value); return prop; } diff --git a/libX11/src/xkb/XKBGeom.c b/libX11/src/xkb/XKBGeom.c index c42a453e4..ea52b85f1 100644 --- a/libX11/src/xkb/XKBGeom.c +++ b/libX11/src/xkb/XKBGeom.c @@ -265,10 +265,9 @@ _XkbReadGeomProperties(XkbReadBufferPtr buf, ok = _XkbGetReadBufferCountedString(buf, &name) && ok; ok = _XkbGetReadBufferCountedString(buf, &value) && ok; ok = ok && (XkbAddGeomProperty(geom, name, value) != NULL); - if (name) - _XkbFree(name); - if (value) - _XkbFree(value); + + _XkbFree(name); + _XkbFree(value); } if (ok) rtrn = Success; @@ -318,8 +317,8 @@ _XkbReadGeomColors(XkbReadBufferPtr buf, rtrn = BadLength; else if (XkbAddGeomColor(geom, spec, geom->num_colors) == NULL) rtrn = BadAlloc; - if (spec) - _XkbFree(spec); + + _XkbFree(spec); if (rtrn != Success) return rtrn; } diff --git a/libX11/src/xkb/XKBMAlloc.c b/libX11/src/xkb/XKBMAlloc.c index f27fe4ec3..0b86aa1d5 100644 --- a/libX11/src/xkb/XKBMAlloc.c +++ b/libX11/src/xkb/XKBMAlloc.c @@ -226,18 +226,16 @@ XkbCopyKeyType(XkbKeyTypePtr from, XkbKeyTypePtr into) { if ((!from) || (!into)) return BadMatch; - if (into->map) { - _XkbFree(into->map); - into->map = NULL; - } - if (into->preserve) { - _XkbFree(into->preserve); - into->preserve = NULL; - } - if (into->level_names) { - _XkbFree(into->level_names); - into->level_names = NULL; - } + + _XkbFree(into->map); + into->map = NULL; + + _XkbFree(into->preserve); + into->preserve = NULL; + + _XkbFree(into->level_names); + into->level_names = NULL; + *into = *from; if ((from->map) && (into->map_count > 0)) { into->map = _XkbTypedCalloc(into->map_count, XkbKTMapEntryRec); @@ -385,11 +383,9 @@ XkbResizeKeyType(XkbDescPtr xkb, } type = &xkb->map->types[type_ndx]; if (map_count == 0) { - if (type->map != NULL) - _XkbFree(type->map); + _XkbFree(type->map); type->map = NULL; - if (type->preserve != NULL) - _XkbFree(type->preserve); + _XkbFree(type->preserve); type->preserve = NULL; type->map_count = 0; } @@ -400,8 +396,7 @@ XkbResizeKeyType(XkbDescPtr xkb, type->map = _XkbTypedRealloc(type->map, map_count, XkbKTMapEntryRec); if (!type->map) { - if (prev_map) - _XkbFree(prev_map); + _XkbFree(prev_map); return BadAlloc; } if (want_preserve) { @@ -412,12 +407,11 @@ XkbResizeKeyType(XkbDescPtr xkb, XkbModsRec); } if (!type->preserve) { - if (prev_preserve) - _XkbFree(prev_preserve); + _XkbFree(prev_preserve); return BadAlloc; } } - else if (type->preserve != NULL) { + else { _XkbFree(type->preserve); type->preserve = NULL; } @@ -430,8 +424,7 @@ XkbResizeKeyType(XkbDescPtr xkb, type->level_names = _XkbTypedRealloc(type->level_names, new_num_lvls, Atom); if (!type->level_names) { - if (prev_level_names) - _XkbFree(prev_level_names); + _XkbFree(prev_level_names); return BadAlloc; } } @@ -919,19 +912,16 @@ XkbFreeClientMap(XkbDescPtr xkb, unsigned what, Bool freeMap) XkbKeyTypePtr type; for (i = 0, type = map->types; i < map->num_types; i++, type++) { - if (type->map != NULL) { - _XkbFree(type->map); - type->map = NULL; - } - if (type->preserve != NULL) { - _XkbFree(type->preserve); - type->preserve = NULL; - } + _XkbFree(type->map); + type->map = NULL; + + _XkbFree(type->preserve); + type->preserve = NULL; + type->map_count = 0; - if (type->level_names != NULL) { - _XkbFree(type->level_names); - type->level_names = NULL; - } + + _XkbFree(type->level_names); + type->level_names = NULL; } } _XkbFree(map->types); @@ -940,17 +930,14 @@ XkbFreeClientMap(XkbDescPtr xkb, unsigned what, Bool freeMap) } } if (what & XkbKeySymsMask) { - if (map->key_sym_map != NULL) { - _XkbFree(map->key_sym_map); - map->key_sym_map = NULL; - } - if (map->syms != NULL) { - _XkbFree(map->syms); - map->size_syms = map->num_syms = 0; - map->syms = NULL; - } + _XkbFree(map->key_sym_map); + map->key_sym_map = NULL; + + _XkbFree(map->syms); + map->size_syms = map->num_syms = 0; + map->syms = NULL; } - if ((what & XkbModifierMapMask) && (map->modmap != NULL)) { + if (what & XkbModifierMapMask) { _XkbFree(map->modmap); map->modmap = NULL; } @@ -971,26 +958,23 @@ XkbFreeServerMap(XkbDescPtr xkb, unsigned what, Bool freeMap) if (freeMap) what = XkbAllServerInfoMask; map = xkb->server; - if ((what & XkbExplicitComponentsMask) && (map->explicit != NULL)) { + if (what & XkbExplicitComponentsMask) { _XkbFree(map->explicit); map->explicit = NULL; } if (what & XkbKeyActionsMask) { - if (map->key_acts != NULL) { - _XkbFree(map->key_acts); + _XkbFree(map->key_acts); map->key_acts = NULL; - } - if (map->acts != NULL) { - _XkbFree(map->acts); + + _XkbFree(map->acts); map->num_acts = map->size_acts = 0; map->acts = NULL; - } } - if ((what & XkbKeyBehaviorsMask) && (map->behaviors != NULL)) { + if (what & XkbKeyBehaviorsMask) { _XkbFree(map->behaviors); map->behaviors = NULL; } - if ((what & XkbVirtualModMapMask) && (map->vmodmap != NULL)) { + if (what & XkbVirtualModMapMask) { _XkbFree(map->vmodmap); map->vmodmap = NULL; } diff --git a/libX11/src/xkb/XKBNames.c b/libX11/src/xkb/XKBNames.c index 5a3fb6f8d..6c4800c29 100644 --- a/libX11/src/xkb/XKBNames.c +++ b/libX11/src/xkb/XKBNames.c @@ -133,8 +133,8 @@ _XkbReadGetNamesReply(Display *dpy, if ((nLevels[i] > 0) && (nLevels[i] != type->num_levels)) { goto BAILOUT; } - if (type->level_names != NULL) - Xfree(type->level_names); + + Xfree(type->level_names); if (nLevels[i] == 0) { type->level_names = NULL; continue; diff --git a/libX11/src/xkb/XKBRdBuf.c b/libX11/src/xkb/XKBRdBuf.c index 8e9eab238..0a29bdca4 100644 --- a/libX11/src/xkb/XKBRdBuf.c +++ b/libX11/src/xkb/XKBRdBuf.c @@ -167,8 +167,8 @@ _XkbFreeReadBuffer(XkbReadBufferPtr buf) int left; left = (int) _XkbReadBufferDataLeft(buf); - if (buf->start != NULL) - Xfree(buf->start); + + Xfree(buf->start); buf->size = 0; buf->start = buf->data = NULL; return left; diff --git a/libX11/src/xlibi18n/ICWrap.c b/libX11/src/xlibi18n/ICWrap.c index 2a1d0d670..8c1b4a01c 100644 --- a/libX11/src/xlibi18n/ICWrap.c +++ b/libX11/src/xlibi18n/ICWrap.c @@ -186,7 +186,7 @@ XSetIMValues(XIM im, ...) va_end(var); ret = (*im->methods->set_values) (im, args); - if (args) Xfree(args); + Xfree(args); return ret; } @@ -213,7 +213,7 @@ XGetIMValues(XIM im, ...) va_end(var); ret = (*im->methods->get_values) (im, args); - if (args) Xfree(args); + Xfree(args); return ret; } @@ -245,7 +245,7 @@ XCreateIC(XIM im, ...) va_end(var); ic = (XIC) (*im->methods->create_ic) (im, args); - if (args) Xfree(args); + Xfree(args); if (ic) { ic->core.next = im->core.ic_chain; im->core.ic_chain = ic; @@ -300,7 +300,7 @@ XGetICValues(XIC ic, ...) va_end(var); ret = (*ic->methods->get_values) (ic, args); - if (args) Xfree(args); + Xfree(args); return ret; } @@ -330,7 +330,7 @@ XSetICValues(XIC ic, ...) va_end(var); ret = (*ic->methods->set_values) (ic, args); - if (args) Xfree(args); + Xfree(args); return ret; } diff --git a/libX11/src/xlibi18n/XDefaultOMIF.c b/libX11/src/xlibi18n/XDefaultOMIF.c index 2ff6c414c..007b443a1 100644 --- a/libX11/src/xlibi18n/XDefaultOMIF.c +++ b/libX11/src/xlibi18n/XDefaultOMIF.c @@ -369,8 +369,8 @@ init_core_part( return True; err: - if (font_name_list) - Xfree(font_name_list); + + Xfree(font_name_list); Xfree(font_struct_list); return False; @@ -638,14 +638,10 @@ destroy_oc( XOCGenericPart *gen = XOC_GENERIC(oc); XFontStruct **font_list, *font; - if (gen->font_set) - Xfree(gen->font_set); - - if (oc->core.base_name_list) - Xfree(oc->core.base_name_list); - if (oc->core.font_info.font_name_list) - XFreeStringList(oc->core.font_info.font_name_list); + Xfree(gen->font_set); + Xfree(oc->core.base_name_list); + XFreeStringList(oc->core.font_info.font_name_list); if ((font_list = oc->core.font_info.font_struct_list)) { if ((font = *font_list)) { @@ -657,14 +653,12 @@ destroy_oc( Xfree(oc->core.font_info.font_struct_list); } - if (oc->core.missing_list.charset_list) - XFreeStringList(oc->core.missing_list.charset_list); + + XFreeStringList(oc->core.missing_list.charset_list); #ifdef notdef - if (oc->core.res_name) - Xfree(oc->core.res_name); - if (oc->core.res_class) - Xfree(oc->core.res_class); + Xfree(oc->core.res_name); + Xfree(oc->core.res_class); #endif Xfree(oc); @@ -1045,7 +1039,6 @@ close_om( if (data->font_data) { for (font_data = data->font_data, count = data->font_data_count; count-- > 0 ; font_data++) { - if (font_data->name) Xfree(font_data->name); } Xfree(data->font_data); @@ -1053,17 +1046,16 @@ close_om( Xfree(gen->data); } - if (om->core.res_name) - Xfree(om->core.res_name); - if (om->core.res_class) - Xfree(om->core.res_class); + + Xfree(om->core.res_name); + Xfree(om->core.res_class); + if (om->core.required_charset.charset_list) XFreeStringList(om->core.required_charset.charset_list); else Xfree((char*)om->core.required_charset.charset_list); - if (om->core.orientation_list.orientation) - Xfree(om->core.orientation_list.orientation); + Xfree(om->core.orientation_list.orientation); Xfree(om); return 1; diff --git a/libX11/src/xlibi18n/lcFile.c b/libX11/src/xlibi18n/lcFile.c index c3ea02ead..f74147496 100644 --- a/libX11/src/xlibi18n/lcFile.c +++ b/libX11/src/xlibi18n/lcFile.c @@ -554,7 +554,7 @@ _XlcResolveLocaleName( break; } } - if (nlc_name) Xfree(nlc_name); + Xfree(nlc_name); if (name == NULL) { /* vendor locale name == Xlocale name, no expansion of alias */ @@ -672,19 +672,18 @@ _XlcLocaleDirName(char *dir_name, size_t dir_len, const char *lc_name) target_name = NULL; } } - if (nlc_name) Xfree(nlc_name); + Xfree(nlc_name); if (target_name == NULL) /* vendor locale name == Xlocale name, no expansion of alias */ snprintf(dir_name, dir_len, "%s/%s", args[0], lc_name); else snprintf(dir_name, dir_len, "%s/%s", target_dir, target_name); + Xfree(target_name); + Xfree (last_dir_name); + Xfree (last_lc_name); - if (last_dir_name != 0) - Xfree (last_dir_name); - if (last_lc_name != 0) - Xfree (last_lc_name); last_dir_len = strlen (dir_name) + 1; last_dir_name = Xmalloc (last_dir_len); strcpy (last_dir_name, dir_name); @@ -751,7 +750,7 @@ _XlcLocaleLibDirName(char *dir_name, size_t dir_len, const char *lc_name) target_name = NULL; } } - if (nlc_name) Xfree(nlc_name); + Xfree(nlc_name); if (target_name == NULL) /* vendor locale name == Xlocale name, no expansion of alias */ @@ -759,11 +758,9 @@ _XlcLocaleLibDirName(char *dir_name, size_t dir_len, const char *lc_name) else snprintf(dir_name, dir_len, "%s/%s", target_dir, target_name); Xfree(target_name); + Xfree (last_dir_name); + Xfree (last_lc_name); - if (last_dir_name != 0) - Xfree (last_dir_name); - if (last_lc_name != 0) - Xfree (last_lc_name); last_dir_len = strlen (dir_name) + 1; last_dir_name = Xmalloc (last_dir_len); strcpy (last_dir_name, dir_name); diff --git a/libX11/src/xlibi18n/lcGeneric.c b/libX11/src/xlibi18n/lcGeneric.c index 13405a65b..ba8dd7028 100644 --- a/libX11/src/xlibi18n/lcGeneric.c +++ b/libX11/src/xlibi18n/lcGeneric.c @@ -260,8 +260,8 @@ add_parse_list( err: Xfree(str); - if (new) - Xfree(new); + + Xfree(new); return False; } @@ -274,12 +274,10 @@ free_charset( ParseInfo *parse_info; int num; - if (gen->mb_parse_table) - Xfree(gen->mb_parse_table); + Xfree(gen->mb_parse_table); if ((num = gen->mb_parse_list_num) > 0) { for (parse_info = gen->mb_parse_list; num-- > 0; parse_info++) { - if ((*parse_info)->encoding) - Xfree((*parse_info)->encoding); + Xfree((*parse_info)->encoding); Xfree(*parse_info); } Xfree(gen->mb_parse_list); diff --git a/libX11/src/xlibi18n/lcPrTxt.c b/libX11/src/xlibi18n/lcPrTxt.c index 47d11f096..72fc2b927 100644 --- a/libX11/src/xlibi18n/lcPrTxt.c +++ b/libX11/src/xlibi18n/lcPrTxt.c @@ -283,8 +283,7 @@ _XwcFreeStringList( wchar_t **list) { if (list) { - if (*list) - Xfree(*list); + Xfree(*list); Xfree(list); } } diff --git a/libX11/src/xlibi18n/lcPublic.c b/libX11/src/xlibi18n/lcPublic.c index 46c652e2b..8e817a8cc 100644 --- a/libX11/src/xlibi18n/lcPublic.c +++ b/libX11/src/xlibi18n/lcPublic.c @@ -255,16 +255,14 @@ static void destroy_core( XLCd lcd) { - if (lcd->core) { - if (lcd->core->name) + if (lcd) { + if (lcd->core) { Xfree(lcd->core->name); - Xfree(lcd->core); + Xfree(lcd->core); + } + Xfree(lcd->methods); + Xfree(lcd); } - - if (lcd->methods) - Xfree(lcd->methods); - - Xfree(lcd); } static void @@ -275,10 +273,8 @@ destroy( _XlcDestroyLocaleDataBase(lcd); - if (pub->siname) - Xfree(pub->siname); - if (pub->encoding_name) - Xfree(pub->encoding_name); + Xfree(pub->siname); + Xfree(pub->encoding_name); destroy_core(lcd); } diff --git a/libX11/src/xlibi18n/lcWrap.c b/libX11/src/xlibi18n/lcWrap.c index 034bd3c0d..382426082 100644 --- a/libX11/src/xlibi18n/lcWrap.c +++ b/libX11/src/xlibi18n/lcWrap.c @@ -86,8 +86,7 @@ XSetLocaleModifiers( user_mods = getenv("XMODIFIERS"); mapped_mods = (*lcd->methods->map_modifiers) (lcd, user_mods, modifiers); if (mapped_mods) { - if (lcd->core->modifiers) - Xfree(lcd->core->modifiers); + Xfree(lcd->core->modifiers); lcd->core->modifiers = mapped_mods; } return mapped_mods; diff --git a/libxcb/src/c_client.py b/libxcb/src/c_client.py index af1337ec0..e3f191b90 100644 --- a/libxcb/src/c_client.py +++ b/libxcb/src/c_client.py @@ -1549,6 +1549,17 @@ def _c_accessors_list(self, field): Declares a direct-accessor function only if the list members are fixed size. Declares length and get-iterator functions always. ''' + + def get_align_pad(field): + prev = field.prev_varsized_field + prev_prev = field.prev_varsized_field.prev_varsized_field + + if (prev.type.is_pad and prev.type.align > 0 and prev_prev is not None): + return (prev_prev, '((-prev.index) & (%d - 1))' % prev.type.align) + else: + return (prev, None) + + list = field.type c_type = self.c_type @@ -1624,9 +1635,16 @@ def _c_accessors_list(self, field): elif field.prev_varsized_field is None: _c(' return (%s *) (R + 1);', field.c_field_type) else: - _c(' xcb_generic_iterator_t prev = %s;', _c_iterator_get_end(field.prev_varsized_field, 'R')) - _c(' return (%s *) ((char *) prev.data + XCB_TYPE_PAD(%s, prev.index) + %d);', - field.c_field_type, type_pad_type(field.first_field_after_varsized.type.c_type), field.prev_varsized_offset) + (prev_varsized_field, align_pad) = get_align_pad(field) + + if align_pad is None: + align_pad = ('XCB_TYPE_PAD(%s, prev.index)' % + type_pad_type(field.first_field_after_varsized.type.c_type)) + + _c(' xcb_generic_iterator_t prev = %s;', + _c_iterator_get_end(prev_varsized_field, 'R')) + _c(' return (%s *) ((char *) prev.data + %s + %d);', + field.c_field_type, align_pad, field.prev_varsized_offset) _c('}') _hc('') @@ -1728,9 +1746,17 @@ def _c_accessors_list(self, field): elif field.prev_varsized_field == None: _c(' i.data = (%s *) (R + 1);', field.c_field_type) else: - _c(' xcb_generic_iterator_t prev = %s;', _c_iterator_get_end(field.prev_varsized_field, 'R')) - _c(' i.data = (%s *) ((char *) prev.data + XCB_TYPE_PAD(%s, prev.index));', - field.c_field_type, type_pad_type(field.c_field_type)) + (prev_varsized_field, align_pad) = get_align_pad(field) + + if align_pad is None: + align_pad = ('XCB_TYPE_PAD(%s, prev.index)' % + type_pad_type(field.c_field_type)) + + _c(' xcb_generic_iterator_t prev = %s;', + _c_iterator_get_end(prev_varsized_field, 'R')) + _c(' i.data = (%s *) ((char *) prev.data + %s);', + field.c_field_type, align_pad) + if switch_obj is None: _c(' i.rem = %s;', _c_accessor_get_expr(field.type.expr, fields)) _c(' i.index = (char *) i.data - (char *) %s;', 'R' if switch_obj is None else 'S' ) diff --git a/libxcb/src/xcb.h b/libxcb/src/xcb.h index ec5cd3301..b180be8ef 100644 --- a/libxcb/src/xcb.h +++ b/libxcb/src/xcb.h @@ -458,7 +458,8 @@ int xcb_get_file_descriptor(xcb_connection_t *c); * Some errors that occur in the context of an xcb_connection_t * are unrecoverable. When such an error occurs, the * connection is shut down and further operations on the - * xcb_connection_t have no effect. + * xcb_connection_t have no effect, but memory will not be freed until + * xcb_disconnect() is called on the xcb_connection_t. * * @return XCB_CONN_ERROR, because of socket errors, pipe errors or other stream errors. * @return XCB_CONN_CLOSED_EXT_NOTSUPPORTED, when extension not supported. @@ -480,6 +481,11 @@ int xcb_connection_has_error(xcb_connection_t *c); * bidirectionally connected to an X server. If the connection * should be unauthenticated, @p auth_info must be @c * NULL. + * + * Always returns a non-NULL pointer to a xcb_connection_t, even on failure. + * Callers need to use xcb_connection_has_error() to check for failure. + * When finished, use xcb_disconnect() to close the connection and free + * the structure. */ xcb_connection_t *xcb_connect_to_fd(int fd, xcb_auth_info_t *auth_info); @@ -525,6 +531,11 @@ int xcb_parse_display(const char *name, char **host, int *display, int *screen); * variable. If a particular screen on that server is preferred, the * int pointed to by @p screenp (if not @c NULL) will be set to that * screen; otherwise the screen will be set to 0. + * + * Always returns a non-NULL pointer to a xcb_connection_t, even on failure. + * Callers need to use xcb_connection_has_error() to check for failure. + * When finished, use xcb_disconnect() to close the connection and free + * the structure. */ xcb_connection_t *xcb_connect(const char *displayname, int *screenp); @@ -539,6 +550,11 @@ xcb_connection_t *xcb_connect(const char *displayname, int *screenp); * authorization @p auth. If a particular screen on that server is * preferred, the int pointed to by @p screenp (if not @c NULL) will * be set to that screen; otherwise @p screenp will be set to 0. + * + * Always returns a non-NULL pointer to a xcb_connection_t, even on failure. + * Callers need to use xcb_connection_has_error() to check for failure. + * When finished, use xcb_disconnect() to close the connection and free + * the structure. */ xcb_connection_t *xcb_connect_to_display_with_auth_info(const char *display, xcb_auth_info_t *auth, int *screen); diff --git a/libxcb/src/xcb_in.c b/libxcb/src/xcb_in.c index 559a6e3ea..dfcd1ecd8 100644 --- a/libxcb/src/xcb_in.c +++ b/libxcb/src/xcb_in.c @@ -36,9 +36,6 @@ #include <stdio.h> #include <errno.h> -#include "xcb.h" -#include "xcbext.h" -#include "xcbint.h" #if USE_POLL #include <poll.h> #endif @@ -51,6 +48,10 @@ #include "xcb_windefs.h" #endif /* _WIN32 */ +#include "xcb.h" +#include "xcbext.h" +#include "xcbint.h" + #define XCB_ERROR 0 #define XCB_REPLY 1 #define XCB_XGE_EVENT 35 diff --git a/libxcb/xcb-proto/src/dri2.xml b/libxcb/xcb-proto/src/dri2.xml index 20d664912..3b4c12e9b 100644 --- a/libxcb/xcb-proto/src/dri2.xml +++ b/libxcb/xcb-proto/src/dri2.xml @@ -133,7 +133,10 @@ authorization from the authors. <request name="GetBuffers" opcode="5"> <field type="DRAWABLE" name="drawable" /> <field type="CARD32" name="count" /> - <list type="CARD32" name="attachments" /> + <list type="CARD32" name="attachments"> + <!-- The length field should be linked but we can't correct it without breaking API --> + <!-- <fieldref>count</fieldref> --> + </list> <reply> <pad bytes="1" /> <field type="CARD32" name="width" /> @@ -159,7 +162,10 @@ authorization from the authors. <request name="GetBuffersWithFormat" opcode="7"> <field type="DRAWABLE" name="drawable" /> <field type="CARD32" name="count" /> - <list type="AttachFormat" name="attachments" /> + <list type="AttachFormat" name="attachments"> + <!-- The length field should be linked but we can't correct it without breaking API --> + <!-- <fieldref>count</fieldref> --> + </list> <reply> <pad bytes="1" /> <field type="CARD32" name="width" /> diff --git a/libxcb/xcb-proto/src/xv.xml b/libxcb/xcb-proto/src/xv.xml index 0b55d3633..47a05d04d 100644 --- a/libxcb/xcb-proto/src/xv.xml +++ b/libxcb/xcb-proto/src/xv.xml @@ -101,6 +101,7 @@ authorization from the authors. <list type="char" name="name"> <fieldref>name_size</fieldref> </list> + <pad align="4" /> <list type="Format" name="formats"> <fieldref>num_formats</fieldref> </list> diff --git a/mesalib/configure.ac b/mesalib/configure.ac index a12f27ac2..e4cfb07ee 100644 --- a/mesalib/configure.ac +++ b/mesalib/configure.ac @@ -149,7 +149,7 @@ _SAVE_LDFLAGS="$LDFLAGS" _SAVE_CPPFLAGS="$CPPFLAGS" dnl Compiler macros -DEFINES="" +DEFINES="-DUSE_EXTERNAL_DXTN_LIB=1" AC_SUBST([DEFINES]) case "$host_os" in linux*|*-gnu*|gnu*) @@ -543,7 +543,7 @@ darwin*|mingw*) *) AC_CHECK_FUNCS([clock_gettime], [CLOCK_LIB=], [AC_CHECK_LIB([rt], [clock_gettime], [CLOCK_LIB=-lrt], - [AC_MSG_ERROR([Couldn't find clock_gettime])])]) + [AC_MSG_ERROR([Could not find clock_gettime])])]) AC_SUBST([CLOCK_LIB]) ;; esac @@ -902,26 +902,12 @@ if test "x$enable_dri" = xyes; then fi fi -dnl Direct rendering or just indirect rendering -case "$host_os" in -gnu*) - dnl Disable by default on GNU/Hurd - driglx_direct_default="no" - ;; -cygwin*) - dnl Disable by default on cygwin - driglx_direct_default="no" - ;; -*) - driglx_direct_default="yes" - ;; -esac AC_ARG_ENABLE([driglx-direct], [AS_HELP_STRING([--disable-driglx-direct], [disable direct rendering in GLX and EGL for DRI \ @<:@default=auto@:>@])], [driglx_direct="$enableval"], - [driglx_direct="$driglx_direct_default"]) + [driglx_direct="yes"]) dnl dnl libGL configuration per driver @@ -945,6 +931,7 @@ xyesno) if test x"$driglx_direct" = xyes; then if test x"$dri_platform" = xdrm ; then + DEFINES="$DEFINES -DGLX_USE_DRM" if test "x$have_libdrm" != xyes; then AC_MSG_ERROR([Direct rendering requires libdrm >= $LIBDRM_REQUIRED]) fi @@ -1090,7 +1077,6 @@ if test "x$enable_dri" = xyes; then # Platform specific settings and drivers to build case "$host_os" in linux*) - DEFINES="$DEFINES -DUSE_EXTERNAL_DXTN_LIB=1" DEFINES="$DEFINES -DHAVE_ALIAS" if test "x$enable_dri3" = xyes; then DEFINES="$DEFINES -DHAVE_DRI3" @@ -1110,24 +1096,19 @@ if test "x$enable_dri" = xyes; then esac ;; *freebsd* | dragonfly* | *netbsd* | openbsd*) - DEFINES="$DEFINES -DHAVE_PTHREAD -DUSE_EXTERNAL_DXTN_LIB=1" + DEFINES="$DEFINES -DHAVE_PTHREAD" DEFINES="$DEFINES -DHAVE_ALIAS" ;; gnu*) - DEFINES="$DEFINES -DUSE_EXTERNAL_DXTN_LIB=1" DEFINES="$DEFINES -DHAVE_ALIAS" ;; - solaris*) - DEFINES="$DEFINES -DUSE_EXTERNAL_DXTN_LIB=1" - ;; cygwin*) - DEFINES="$DEFINES -DUSE_EXTERNAL_DXTN_LIB=1" if test "x$with_dri_drivers" = "xyes"; then with_dri_drivers="swrast" fi ;; darwin*) - DEFINES="$DEFINES -DUSE_EXTERNAL_DXTN_LIB=1 -DGLX_ALIAS_UNSUPPORTED" + DEFINES="$DEFINES -DGLX_ALIAS_UNSUPPORTED" if test "x$with_dri_drivers" = "xyes"; then with_dri_drivers="swrast" fi @@ -1375,7 +1356,7 @@ if test "x$enable_xa" = xyes; then if test "x$with_gallium_drivers" = xswrast; then AC_MSG_ERROR([ Building xa requires at least one non swrast gallium driver. - If you are looking to use libxatracker.so with vmware's virtual gpu, + If you are looking to use libxatracker.so with the VMware driver, make sure to include svga in the gallium drivers list, apart from enabling XA. Example: ./configure --enable-xa --with-gallium-drivers=svga...]) @@ -1412,7 +1393,7 @@ AM_CONDITIONAL(HAVE_OPENVG, test "x$enable_openvg" = xyes) dnl dnl Gallium G3DVL configuration dnl -if test -n "$with_gallium_drivers" && ! echo "$with_gallium_drivers" | grep -q 'swrast'; then +if test -n "$with_gallium_drivers" -a "x$with_gallium_drivers" != xswrast; then if test "x$enable_xvmc" = xauto; then PKG_CHECK_EXISTS([xvmc], [enable_xvmc=yes], [enable_xvmc=no]) fi @@ -1429,6 +1410,7 @@ fi if test "x$enable_xvmc" = xyes; then PKG_CHECK_MODULES([XVMC], [xvmc >= $XVMC_REQUIRED x11-xcb xcb-dri2 >= $XCBDRI2_REQUIRED]) GALLIUM_STATE_TRACKERS_DIRS="$GALLIUM_STATE_TRACKERS_DIRS xvmc" + enable_gallium_loader=yes fi AM_CONDITIONAL(HAVE_ST_XVMC, test "x$enable_xvmc" = xyes) @@ -1436,6 +1418,7 @@ if test "x$enable_vdpau" = xyes; then PKG_CHECK_MODULES([VDPAU], [vdpau >= $VDPAU_REQUIRED x11-xcb xcb-dri2 >= $XCBDRI2_REQUIRED], [VDPAU_LIBS="`$PKG_CONFIG --libs x11-xcb xcb-dri2`"]) GALLIUM_STATE_TRACKERS_DIRS="$GALLIUM_STATE_TRACKERS_DIRS vdpau" + enable_gallium_loader=yes fi AM_CONDITIONAL(HAVE_ST_VDPAU, test "x$enable_vdpau" = xyes) @@ -1775,6 +1758,10 @@ if test "x$enable_gallium_llvm" = xyes; then else MESA_LLVM=0 LLVM_VERSION_INT=0 + + if test "x$enable_opencl" = xyes; then + AC_MSG_ERROR([cannot enable OpenCL without LLVM]) + fi fi dnl Directory for XVMC libs @@ -1928,11 +1915,7 @@ if test -n "$with_gallium_drivers"; then HAVE_GALLIUM_I915=yes PKG_CHECK_MODULES([INTEL], [libdrm_intel >= $LIBDRM_INTEL_REQUIRED]) gallium_require_drm_loader - GALLIUM_DRIVERS_DIRS="$GALLIUM_DRIVERS_DIRS i915 softpipe" - if test "x$MESA_LLVM" = x1; then - GALLIUM_DRIVERS_DIRS="$GALLIUM_DRIVERS_DIRS llvmpipe" - fi - GALLIUM_WINSYS_DIRS="$GALLIUM_WINSYS_DIRS i915/sw" + GALLIUM_DRIVERS_DIRS="$GALLIUM_DRIVERS_DIRS i915" gallium_check_st "i915/drm" "dri-i915" DRICOMMON_NEED_LIBDRM=yes ;; @@ -1968,7 +1951,7 @@ if test -n "$with_gallium_drivers"; then if test "x$enable_opencl" = xyes; then LLVM_COMPONENTS="${LLVM_COMPONENTS} bitreader asmparser" fi - gallium_check_st "radeon/drm" "r600/dri" "" "r600/xvmc" "r600/vdpau" "r600/omx" + gallium_check_st "radeon/drm" "r600/dri" "" "xvmc/r600" "vdpau/r600" "r600/omx" DRICOMMON_NEED_LIBDRM=yes ;; xradeonsi) @@ -1978,7 +1961,7 @@ if test -n "$with_gallium_drivers"; then GALLIUM_DRIVERS_DIRS="$GALLIUM_DRIVERS_DIRS radeonsi" radeon_llvm_check "radeonsi" require_egl_drm "radeonsi" - gallium_check_st "radeon/drm" "radeonsi/dri" "" "" "radeonsi/vdpau" "radeonsi/omx" + gallium_check_st "radeon/drm" "radeonsi/dri" "" "" "vdpau/radeonsi" "radeonsi/omx" DRICOMMON_NEED_LIBDRM=yes ;; xnouveau) @@ -1986,7 +1969,7 @@ if test -n "$with_gallium_drivers"; then PKG_CHECK_MODULES([NOUVEAU], [libdrm_nouveau >= $LIBDRM_NOUVEAU_REQUIRED]) gallium_require_drm_loader GALLIUM_DRIVERS_DIRS="$GALLIUM_DRIVERS_DIRS nouveau" - gallium_check_st "nouveau/drm" "dri-nouveau" "" "xvmc-nouveau" "vdpau-nouveau" "omx-nouveau" + gallium_check_st "nouveau/drm" "dri-nouveau" "" "xvmc/nouveau" "vdpau/nouveau" "omx-nouveau" DRICOMMON_NEED_LIBDRM=yes ;; xfreedreno) @@ -2072,12 +2055,14 @@ AM_CONDITIONAL(HAVE_GALLIUM_SOFTPIPE, test "x$HAVE_GALLIUM_SOFTPIPE" = xyes) AM_CONDITIONAL(HAVE_GALLIUM_LLVMPIPE, test "x$HAVE_GALLIUM_LLVMPIPE" = xyes) AM_CONDITIONAL(NEED_GALLIUM_SOFTPIPE_DRIVER, test "x$HAVE_GALLIUM_SVGA" = xyes -o \ - "x$HAVE_GALLIUM_I915" = xyes -o \ "x$HAVE_GALLIUM_SOFTPIPE" = xyes) -AM_CONDITIONAL(NEED_GALLIUM_LLVMPIPE_DRIVER, test "x$HAVE_GALLIUM_I915" = xyes -o \ - "x$HAVE_GALLIUM_SOFTPIPE" = xyes \ +AM_CONDITIONAL(NEED_GALLIUM_LLVMPIPE_DRIVER, test "x$HAVE_GALLIUM_SOFTPIPE" = xyes \ && test "x$MESA_LLVM" = x1) +# Enable static gallium targets for now. +# Do not touch this unless you know what you are doing. +AM_CONDITIONAL(HAVE_GALLIUM_STATIC_TARGETS, test "xyes" = xyes) + # NOTE: anything using xcb or other client side libs ends up in separate # _CLIENT variables. The pipe loader is built in two variants, # one that is standalone and does not link any x client libs (for @@ -2228,30 +2213,26 @@ AC_CONFIG_FILES([Makefile src/gallium/targets/dri-vmwgfx/Makefile src/gallium/targets/egl-static/Makefile src/gallium/targets/gbm/Makefile - src/gallium/targets/opencl/Makefile - src/gallium/targets/xa/Makefile - src/gallium/targets/xa/xatracker.pc + src/gallium/targets/libgl-xlib/Makefile src/gallium/targets/omx-nouveau/Makefile + src/gallium/targets/opencl/Makefile src/gallium/targets/osmesa/Makefile src/gallium/targets/osmesa/osmesa.pc src/gallium/targets/pipe-loader/Makefile - src/gallium/targets/radeonsi/dri/Makefile - src/gallium/targets/radeonsi/omx/Makefile - src/gallium/targets/radeonsi/vdpau/Makefile src/gallium/targets/r300/dri/Makefile src/gallium/targets/r600/dri/Makefile src/gallium/targets/r600/omx/Makefile - src/gallium/targets/r600/vdpau/Makefile - src/gallium/targets/r600/xvmc/Makefile - src/gallium/targets/libgl-xlib/Makefile - src/gallium/targets/vdpau-nouveau/Makefile - src/gallium/targets/xvmc-nouveau/Makefile + src/gallium/targets/radeonsi/dri/Makefile + src/gallium/targets/radeonsi/omx/Makefile + src/gallium/targets/vdpau/Makefile + src/gallium/targets/xa/Makefile + src/gallium/targets/xa/xatracker.pc + src/gallium/targets/xvmc/Makefile src/gallium/tests/trivial/Makefile src/gallium/tests/unit/Makefile src/gallium/winsys/Makefile src/gallium/winsys/freedreno/drm/Makefile src/gallium/winsys/i915/drm/Makefile - src/gallium/winsys/i915/sw/Makefile src/gallium/winsys/intel/drm/Makefile src/gallium/winsys/nouveau/drm/Makefile src/gallium/winsys/radeon/drm/Makefile diff --git a/mesalib/docs/GL3.txt b/mesalib/docs/GL3.txt index d26c8124d..47165fe1e 100644 --- a/mesalib/docs/GL3.txt +++ b/mesalib/docs/GL3.txt @@ -97,7 +97,6 @@ GL 3.3 --- all DONE: i965, nv50, nvc0, r600, radeonsi GL 4.0: GLSL 4.0 not started - GL_ARB_texture_query_lod DONE (i965, nv50, nvc0) GL_ARB_draw_buffers_blend DONE (i965, nv50, nvc0, r600, radeonsi, softpipe) GL_ARB_draw_indirect DONE (i965) GL_ARB_gpu_shader5 started @@ -119,7 +118,8 @@ GL 4.0: GL_ARB_tessellation_shader not started GL_ARB_texture_buffer_object_rgb32 DONE (i965, nvc0, r600, radeonsi, softpipe) GL_ARB_texture_cube_map_array DONE (i965, nv50, nvc0, r600, radeonsi, softpipe) - GL_ARB_texture_gather DONE (i965, nv50, nvc0) + GL_ARB_texture_gather DONE (i965, nv50, nvc0, radeonsi) + GL_ARB_texture_query_lod DONE (i965, nv50, nvc0, radeonsi) GL_ARB_transform_feedback2 DONE (i965, nv50, nvc0, r600, radeonsi) GL_ARB_transform_feedback3 DONE (i965, nv50, nvc0, r600, radeonsi) @@ -132,14 +132,14 @@ GL 4.1: GL_ARB_separate_shader_objects DONE (all drivers) GL_ARB_shader_precision not started GL_ARB_vertex_attrib_64bit not started - GL_ARB_viewport_array DONE (i965, nv50, r600) + GL_ARB_viewport_array DONE (i965, nv50, nvc0, r600) GL 4.2: GLSL 4.2 not started GL_ARB_texture_compression_bptc not started - GL_ARB_compressed_texture_pixel_storage not started + GL_ARB_compressed_texture_pixel_storage DONE (all drivers) GL_ARB_shader_atomic_counters DONE (i965) GL_ARB_texture_storage DONE (all drivers) GL_ARB_transform_feedback_instanced DONE (i965, nv50, nvc0, r600, radeonsi) @@ -160,7 +160,7 @@ GL 4.3: GL_ARB_compute_shader started (Paul Berry) GL_ARB_copy_image not started GL_KHR_debug DONE (all drivers) - GL_ARB_explicit_uniform_location not started + GL_ARB_explicit_uniform_location DONE (all drivers that support GLSL) GL_ARB_fragment_layer_viewport not started GL_ARB_framebuffer_no_attachments not started GL_ARB_internalformat_query2 not started @@ -172,7 +172,7 @@ GL 4.3: GL_ARB_shader_storage_buffer_object not started GL_ARB_stencil_texturing DONE (i965/gen8+, nv50, nvc0, r600, radeonsi) GL_ARB_texture_buffer_range DONE (nv50, nvc0, i965, r600, radeonsi) - GL_ARB_texture_query_levels DONE (i965) + GL_ARB_texture_query_levels DONE (all drivers that support GLSL 1.30) GL_ARB_texture_storage_multisample DONE (all drivers that support GL_ARB_texture_multisample) GL_ARB_texture_view DONE (i965) GL_ARB_vertex_attrib_binding DONE (all drivers) diff --git a/mesalib/docs/index.html b/mesalib/docs/index.html index 2e78343de..fc36c3db0 100644 --- a/mesalib/docs/index.html +++ b/mesalib/docs/index.html @@ -16,6 +16,14 @@ <h1>News</h1> +<h2>June 24, 2014</h2> +<p> +<a href="relnotes/10.1.6.html">Mesa 10.1.6</a> +and <a href="relnotes/10.2.2.html">Mesa 10.2.2</a> are released. + +These are bug-fix releases from the 10.1 and 10.2 branches, respectively. +</p> + <h2>June 6, 2014</h2> <p> <a href="relnotes/10.2.1.html">Mesa 10.2.1</a> is released. This release @@ -29,6 +37,10 @@ only fixes a build error in the radeonsi driver that was introduced between development release. See the release notes for more information about the release. </p> +<p> +Also, <a href="relnotes/10.1.5.html">Mesa 10.1.5</a> is released. +This is a bug fix release from the 10.1 branch. +</p> <h2>May 20, 2014</h2> <p> diff --git a/mesalib/docs/relnotes.html b/mesalib/docs/relnotes.html index 60d007326..67c19555c 100644 --- a/mesalib/docs/relnotes.html +++ b/mesalib/docs/relnotes.html @@ -21,8 +21,11 @@ The release notes summarize what's new or changed in each Mesa release. </p> <ul> +<li><a href="relnotes/10.2.2.html">10.2.2 release notes</a> <li><a href="relnotes/10.2.1.html">10.2.1 release notes</a> <li><a href="relnotes/10.2.html">10.2 release notes</a> +<li><a href="relnotes/10.1.6.html">10.1.6 release notes</a> +<li><a href="relnotes/10.1.5.html">10.1.5 release notes</a> <li><a href="relnotes/10.1.4.html">10.1.4 release notes</a> <li><a href="relnotes/10.1.3.html">10.1.3 release notes</a> <li><a href="relnotes/10.1.2.html">10.1.2 release notes</a> diff --git a/mesalib/docs/relnotes/10.1.5.html b/mesalib/docs/relnotes/10.1.5.html new file mode 100644 index 000000000..094df2485 --- /dev/null +++ b/mesalib/docs/relnotes/10.1.5.html @@ -0,0 +1,105 @@ +<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"> +<html lang="en"> +<head> + <meta http-equiv="content-type" content="text/html; charset=utf-8"> + <title>Mesa Release Notes</title> + <link rel="stylesheet" type="text/css" href="../mesa.css"> +</head> +<body> + +<div class="header"> + <h1>The Mesa 3D Graphics Library</h1> +</div> + +<iframe src="../contents.html"></iframe> +<div class="content"> + +<h1>Mesa 10.1.5 Release Notes / (June 6, 2014)</h1> + +<p> +Mesa 10.1.5 is a bug fix release which fixes bugs found since the 10.1.4 release. +</p> + +<p> +Mesa 10.1.5 implements the OpenGL 3.3 API, but the version reported by +glGetString(GL_VERSION) or glGetIntegerv(GL_MAJOR_VERSION) / +glGetIntegerv(GL_MINOR_VERSION) depends on the particular driver being used. +Some drivers don't support all the features required in OpenGL 3.3. OpenGL +3.3 is <strong>only</strong> available if requested at context creation +because compatibility contexts are not supported. +</p> + +<h2>SHA256 checksums</h2> +<pre> +b0aceaa75bc9a9b2d9215a113e2ad488b5cf85c99005a7624f8cf7c37c5d0eaa MesaLib-10.1.5.tar.gz +bc6c5ec7836f254a49d055a29d9aa34c97c54c038f47ad3a00fa57a5fef15bbc MesaLib-10.1.5.tar.bz2 +78b7255cab0af7918945452a84de7989096ebcdd27e99b31c56c0589274cbc77 MesaLib-10.1.5.zip +</pre> + +<h2>New features</h2> +<p>None</p> + +<h2>Bug fixes</h2> + +<p>This list is likely incomplete.</p> + +<ul> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=79115">Bug 79115</a> - </li> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=79421">Bug 79421</a> - </li> + +</ul> + +<h2>Changes</h2> + +<p>Brian Paul (1):</p> +<ul> + <li>glsl: fix use-after free bug/crash in ast_declarator_list::hir()</li> +</ul> + +<p>Carl Worth (5):</p> +<ul> + <li>docs: Add md5sums for 10.1.4 release</li> + <li>Merge remote-tracking branch 'origin/10.1' into 10.1</li> + <li>cherry-ignore: Ignore two commits.</li> + <li>Ignore a patch that is not needed for the 10.1 branch.</li> + <li>Update version to 10.1.5</li> +</ul> + +<p>Emil Velikov (1):</p> +<ul> + <li>glx: do not leak dri3Display</li> +</ul> + +<p>Ilia Mirkin (2):</p> +<ul> + <li>nv50/ir: fix s32 x s32 -> high s32 multiply logic</li> + <li>nv50/ir: fix constant folding for OP_MUL subop HIGH</li> +</ul> + +<p>James Legg (1):</p> +<ul> + <li>mesa: Fix unbinding GL_DEPTH_STENCIL_ATTACHMENT</li> +</ul> + +<p>Jeremy Huddleston Sequoia (2):</p> +<ul> + <li>glapi: Avoid heap corruption in _glapi_table</li> + <li>darwin: Fix test for kCGLPFAOpenGLProfile support at runtime</li> +</ul> + +<p>Pavel Popov (2):</p> +<ul> + <li>i965: Properly return *RESET* status in glGetGraphicsResetStatusARB</li> + <li>i965: Fix Line Stipple enable bit in 3DSTATE_SF for Haswell.</li> +</ul> + +<p>Roland Scheidegger (1):</p> +<ul> + <li>llvmpipe: fix crash when not all attachments are populated in a fb</li> +</ul> + +</div> +</body> +</html> diff --git a/mesalib/docs/relnotes/10.1.6.html b/mesalib/docs/relnotes/10.1.6.html new file mode 100644 index 000000000..026acb25a --- /dev/null +++ b/mesalib/docs/relnotes/10.1.6.html @@ -0,0 +1,138 @@ +<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"> +<html lang="en"> +<head> + <meta http-equiv="content-type" content="text/html; charset=utf-8"> + <title>Mesa Release Notes</title> + <link rel="stylesheet" type="text/css" href="../mesa.css"> +</head> +<body> + +<div class="header"> + <h1>The Mesa 3D Graphics Library</h1> +</div> + +<iframe src="../contents.html"></iframe> +<div class="content"> + +<h1>Mesa 10.1.6 Release Notes / (June 24, 2014)</h1> + +<p> +Mesa 10.1.6 is a bug fix release which fixes bugs found since the 10.1.5 release. +</p> + +<p> +Mesa 10.1.6 implements the OpenGL 3.3 API, but the version reported by +glGetString(GL_VERSION) or glGetIntegerv(GL_MAJOR_VERSION) / +glGetIntegerv(GL_MINOR_VERSION) depends on the particular driver being used. +Some drivers don't support all the features required in OpenGL 3.3. OpenGL +3.3 is <strong>only</strong> available if requested at context creation +because compatibility contexts are not supported. +</p> + +<h2>SHA256 checksums</h2> +<pre> +cde60e06b340d7598802fe4a4484b3fb8befd714f9ab9caabe1f27d3149e8815 MesaLib-10.1.6.tar.bz2 +e4e726d7805a442f7ed07d12f71335e6126796ec85328a5989eb5348a8042d00 MesaLib-10.1.6.tar.gz +bf7e3f721a7ad0c2057a034834b6fea688e64f26a66cf8d1caa2827e405e72dd MesaLib-10.1.6.zip +</pre> + +<h2>New features</h2> +<p>None</p> + +<h2>Bug fixes</h2> + +<p>This list is likely incomplete.</p> + +<ul> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=54372">Bug 54372</a> - GLX_INTEL_swap_event crashes driver when swapping window buffers</li> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=74005">Bug 74005</a> - [i965 Bisected]Piglit/glx_glx-make-glxdrawable-current fails</li> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=78581">Bug 78581</a> - </li> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=79729">Bug 79729</a> - [i965] glClear on a multisample texture doesn't work</li> + +</ul> + +<h2>Changes</h2> + +<p>Adrian Negreanu (7):</p> +<ul> + <li>add megadriver_stub_FILES</li> + <li>android: adapt to the megadriver mechanism</li> + <li>android: add libloader to libGLES_mesa and libmesa_egl_dri2</li> + <li>android: add src/gallium/auxiliary as include path for libmesa_dricore</li> + <li>android, egl: add correct drm include for libmesa_egl_dri2</li> + <li>android, mesa_gen_matypes: pull in timespec POSIX definition</li> + <li>android, dricore: undefined reference to _mesa_streaming_load_memcpy</li> +</ul> + +<p>Beren Minor (1):</p> +<ul> + <li>egl/main: Fix eglMakeCurrent when releasing context from current thread.</li> +</ul> + +<p>Carl Worth (3):</p> +<ul> + <li>docs: Add SHA256 checksums for the 10.1.5 release</li> + <li>cherry-ignore: Add a patch to ignore</li> + <li>Update VERSION to 10.1.6</li> +</ul> + +<p>Daniel Manjarres (1):</p> +<ul> + <li>glx: Don't crash on swap event for a Window (non-GLXWindow)</li> +</ul> + +<p>Emil Velikov (1):</p> +<ul> + <li>configure: error out when building opencl without LLVM</li> +</ul> + +<p>Iago Toral Quiroga (1):</p> +<ul> + <li>mesa: Copy Geom.UsesEndPrimitive when cloning a geometry program.</li> +</ul> + +<p>José Fonseca (3):</p> +<ul> + <li>mesa/main: Make get_hash.c values constant.</li> + <li>mesa: Make glGetIntegerv(GL_*_ARRAY_SIZE) return GL_BGRA.</li> + <li>mesa/main: Prevent sefgault on glGetIntegerv(GL_ATOMIC_COUNTER_BUFFER_BINDING).</li> +</ul> + +<p>Kristian Høgsberg (1):</p> +<ul> + <li>mesa: Remove glClear optimization based on drawable size</li> +</ul> + +<p>Michel Dänzer (1):</p> +<ul> + <li>configure: Only check for OpenCL without LLVM when the latter is certain</li> +</ul> + +<p>Neil Roberts (1):</p> +<ul> + <li>i965: Set the fast clear color value for texture surfaces</li> +</ul> + +<p>Roland Scheidegger (1):</p> +<ul> + <li>draw: (trivial) fix clamping of viewport index</li> +</ul> + +<p>Tobias Klausmann (1):</p> +<ul> + <li>nv50/ir: clear subop when folding constant expressions</li> +</ul> + +<p>Tom Stellard (2):</p> +<ul> + <li>clover: Prevent Clang from printing number of errors and warnings to stderr.</li> + <li>clover: Don't use llvm's global context</li> +</ul> + +</div> +</body> +</html> diff --git a/mesalib/docs/relnotes/10.2.1.html b/mesalib/docs/relnotes/10.2.1.html index 81c2acc02..0d67864a7 100644 --- a/mesalib/docs/relnotes/10.2.1.html +++ b/mesalib/docs/relnotes/10.2.1.html @@ -17,7 +17,7 @@ <h1>Mesa 10.2.1 Release Notes / June 6, 2014</h1> <p> -Mesa 10.2.1 is a bug fix release which fixes bugs found since the 10.1 release. +Mesa 10.2.1 is a bug fix release which fixes bugs found since the 10.2 release. </p> <p> Mesa 10.2.1 implements the OpenGL 3.3 API, but the version reported by diff --git a/mesalib/docs/relnotes/10.2.2.html b/mesalib/docs/relnotes/10.2.2.html new file mode 100644 index 000000000..536333dc2 --- /dev/null +++ b/mesalib/docs/relnotes/10.2.2.html @@ -0,0 +1,181 @@ +<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"> +<html lang="en"> +<head> + <meta http-equiv="content-type" content="text/html; charset=utf-8"> + <title>Mesa Release Notes</title> + <link rel="stylesheet" type="text/css" href="../mesa.css"> +</head> +<body> + +<div class="header"> + <h1>The Mesa 3D Graphics Library</h1> +</div> + +<iframe src="../contents.html"></iframe> +<div class="content"> + +<h1>Mesa 10.2.2 Release Notes / June 24, 2014</h1> + +<p> +Mesa 10.2.2 is a bug fix release which fixes bugs found since the 10.2.1 release. +</p> +<p> +Mesa 10.2.2 implements the OpenGL 3.3 API, but the version reported by +glGetString(GL_VERSION) or glGetIntegerv(GL_MAJOR_VERSION) / +glGetIntegerv(GL_MINOR_VERSION) depends on the particular driver being used. +Some drivers don't support all the features required in OpenGL 3.3. OpenGL +3.3 is <strong>only</strong> available if requested at context creation +because compatibility contexts are not supported. +</p> + + +<h2>SHA256 checksums</h2> +<pre> +38c4a40364000f89cddaa1694f6f3cfb444981d1110238ce603093585477399c MesaLib-10.2.2.tar.bz2 +2af2ec8b4db624c352e961eefbcce6c8d1f86d44c5542f6f378c50e1b958d453 MesaLib-10.2.2.tar.gz +d4c0372da59367a344d62ebcdf5cf61039c9cae6925f40f2dab8f8d95cf22da9 MesaLib-10.2.2.zip +</pre> + + +<h2>New features</h2> +<p>None</p> + +<h2>Bug fixes</h2> + +<p>This list is likely incomplete.</p> + +<ul> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=54372">Bug 54372</a> - GLX_INTEL_swap_event crashes driver when swapping window buffers</li> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=66452">Bug 66452</a> - JUNIPER UVD accelerated playback of WMV3 streams does not work</li> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=74005">Bug 74005</a> - [i965 Bisected]Piglit/glx_glx-make-glxdrawable-current fails</li> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=77865">Bug 77865</a> - [BDW] Many Ogles3conform framebuffer_blit cases fail</li> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=78581">Bug 78581</a> - OpenCL: clBuildProgram prints error messages directly rather than storing them</li> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=79029">Bug 79029</a> - INTEL_DEBUG=shader_time is full of lies</li> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=79729">Bug 79729</a> - [i965] glClear on a multisample texture doesn't work</li> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=79907">Bug 79907</a> - Mesa 10.2.1 --enable-vdpau default=auto broken</li> + +<li><a href="https://bugs.freedesktop.org/show_bug.cgi?id=80115">Bug 80115</a> - MESA_META_DRAW_BUFFERS induced GL_INVALID_VALUE errors</li> + +</ul> + + +<h2>Changes</h2> + +<p>Adrian Negreanu (8):</p> +<ul> + <li>add megadriver_stub_FILES</li> + <li>android: adapt to the megadriver mechanism</li> + <li>android: add libloader to libGLES_mesa and libmesa_egl_dri2</li> + <li>android: add src/gallium/auxiliary as include path for libmesa_dricore</li> + <li>android, egl: add correct drm include for libmesa_egl_dri2</li> + <li>android, egl: typo dri2_fallback_pixmap_surface -> dri2_fallback_create_pixmap_surface</li> + <li>android, mesa_gen_matypes: pull in timespec POSIX definition</li> + <li>android, dricore: undefined reference to _mesa_streaming_load_memcpy</li> +</ul> + +<p>Carl Worth (1):</p> +<ul> + <li>Update VERSION to 10.2.2</li> +</ul> + +<p>Daniel Manjarres (1):</p> +<ul> + <li>glx: Don't crash on swap event for a Window (non-GLXWindow)</li> +</ul> + +<p>Emil Velikov (3):</p> +<ul> + <li>targets/xa: limit the amount of exported symbols</li> + <li>configure: error out when building opencl without LLVM</li> + <li>configure: correctly autodetect xvmc/vdpau/omx</li> +</ul> + +<p>Grigori Goronzy (1):</p> +<ul> + <li>radeon/uvd: disable VC-1 simple/main on UVD 2.x</li> +</ul> + +<p>Iago Toral Quiroga (1):</p> +<ul> + <li>mesa: Copy Geom.UsesEndPrimitive when cloning a geometry program.</li> +</ul> + +<p>Ian Romanick (3):</p> +<ul> + <li>docs: Add initial 10.2.1 release notes</li> + <li>docs: Add MD5 checksum, etc. for 10.2.1 release</li> + <li>meta: Respect the driver's maximum number of draw buffers</li> +</ul> + +<p>Ilia Mirkin (7):</p> +<ul> + <li>gk110/ir: emit saturate flag on fadd when needed</li> + <li>gk110/ir: fix emitting constbuf file index</li> + <li>gk110/ir: fix bfind emission</li> + <li>nv50: make sure to mark first scissor dirty after blit</li> + <li>nv30: plug some memory leaks on screen destroy and shader compile</li> + <li>nv30: avoid dangling references to deleted contexts</li> + <li>nv30: hack to avoid errors on unexpected color/zeta combinations</li> +</ul> + +<p>Jason Ekstrand (1):</p> +<ul> + <li>meta_blit: properly compute texture width for the CopyTexSubImage fallback</li> +</ul> + +<p>José Fonseca (1):</p> +<ul> + <li>mesa/main: Prevent sefgault on glGetIntegerv(GL_ATOMIC_COUNTER_BUFFER_BINDING).</li> +</ul> + +<p>Kenneth Graunke (9):</p> +<ul> + <li>i965: Don't use the head sentinel as an fs_inst in Gen4 workaround code.</li> + <li>i965: Invalidate live intervals when inserting Gen4 SEND workarounds.</li> + <li>i965/vec4: Fix dead code elimination for VGRFs of size > 1.</li> + <li>i965: Add missing MOCS setup for 3DSTATE_INDEX_BUFFER on Broadwell.</li> + <li>i965: Drop Broadwell perf_debugs about missing MOCS that aren't missing.</li> + <li>i965: Add missing newlines to a few perf_debug messages.</li> + <li>i965/vec4: Use the sampler for pull constant loads on Broadwell.</li> + <li>i965: Use 8x4 aligned rectangles for HiZ operations on Broadwell.</li> + <li>i965: Save meta stencil blit programs in the context.</li> +</ul> + +<p>Kristian Høgsberg (1):</p> +<ul> + <li>mesa: Remove glClear optimization based on drawable size</li> +</ul> + +<p>Michel Dänzer (1):</p> +<ul> + <li>configure: Only check for OpenCL without LLVM when the latter is certain</li> +</ul> + +<p>Neil Roberts (1):</p> +<ul> + <li>i965: Set the fast clear color value for texture surfaces</li> +</ul> + +<p>Tom Stellard (2):</p> +<ul> + <li>clover: Prevent Clang from printing number of errors and warnings to stderr.</li> + <li>clover: Don't use llvm's global context</li> +</ul> + +<p>Ville Syrjälä (1):</p> +<ul> + <li>i915: Fix gen2 texblend setup</li> +</ul> + + +</div> +</body> +</html> diff --git a/mesalib/docs/relnotes/10.3.html b/mesalib/docs/relnotes/10.3.html index 0c8114bf2..ecc8580f4 100644 --- a/mesalib/docs/relnotes/10.3.html +++ b/mesalib/docs/relnotes/10.3.html @@ -44,9 +44,15 @@ Note: some of the new features are only available with certain drivers. </p> <ul> +<li>GL_ARB_compressed_texture_pixel_storage on all drivers</li> +<li>GL_ARB_explicit_uniform_location (all drivers that support GLSL)</li> <li>GL_ARB_sample_shading on radeonsi</li> <li>GL_ARB_stencil_texturing on nv50, nvc0, r600, and radeonsi</li> <li>GL_ARB_texture_cube_map_array on radeonsi</li> +<li>GL_ARB_texture_gather on radeonsi</li> +<li>GL_ARB_texture_query_levels on nv50, nvc0, llvmpipe, r600, radeonsi, softpipe</li> +<li>GL_ARB_texture_query_lod on radeonsi</li> +<li>GL_ARB_viewport_array on nvc0</li> </ul> diff --git a/mesalib/install-gallium-links.mk b/mesalib/install-gallium-links.mk index 757b28870..f45f1b42b 100644 --- a/mesalib/install-gallium-links.mk +++ b/mesalib/install-gallium-links.mk @@ -5,7 +5,7 @@ if BUILD_SHARED if HAVE_COMPAT_SYMLINKS all-local : .libs/install-gallium-links -.libs/install-gallium-links : $(dri_LTLIBRARIES) $(vdpau_LTLIBRARIES) $(egl_LTLIBRARIES) $(lib_LTLIBRARIES) +.libs/install-gallium-links : $(dri_LTLIBRARIES) $(egl_LTLIBRARIES) $(lib_LTLIBRARIES) $(AM_V_GEN)$(MKDIR_P) $(top_builddir)/$(LIB_DIR); \ link_dir=$(top_builddir)/$(LIB_DIR)/gallium; \ if test x$(egl_LTLIBRARIES) != x; then \ @@ -13,7 +13,6 @@ all-local : .libs/install-gallium-links fi; \ $(MKDIR_P) $$link_dir; \ file_list=$(dri_LTLIBRARIES:%.la=.libs/%.so); \ - file_list+=$(vdpau_LTLIBRARIES:%.la=.libs/%.$(LIB_EXT)*); \ file_list+=$(egl_LTLIBRARIES:%.la=.libs/%.$(LIB_EXT)*); \ file_list+=$(lib_LTLIBRARIES:%.la=.libs/%.$(LIB_EXT)*); \ for f in $$file_list; do \ diff --git a/mesalib/scons/gallium.py b/mesalib/scons/gallium.py index 5109ebffe..e91531971 100644 --- a/mesalib/scons/gallium.py +++ b/mesalib/scons/gallium.py @@ -588,10 +588,9 @@ def generate(env): createInstallMethods(env) env.PkgCheckModules('X11', ['x11', 'xext', 'xdamage', 'xfixes']) - env.PkgCheckModules('XCB', ['x11-xcb', 'xcb-glx >= 1.8.1']) + env.PkgCheckModules('XCB', ['x11-xcb', 'xcb-glx >= 1.8.1', 'xcb-dri2 >= 1.8']) env.PkgCheckModules('XF86VIDMODE', ['xxf86vm']) env.PkgCheckModules('DRM', ['libdrm >= 2.4.38']) - env.PkgCheckModules('DRM_INTEL', ['libdrm_intel >= 2.4.52']) env.PkgCheckModules('UDEV', ['libudev >= 151']) env['dri'] = env['x11'] and env['drm'] diff --git a/mesalib/src/gallium/Automake.inc b/mesalib/src/gallium/Automake.inc index 97735abe0..8bf2a12e8 100644 --- a/mesalib/src/gallium/Automake.inc +++ b/mesalib/src/gallium/Automake.inc @@ -41,6 +41,7 @@ GALLIUM_DRI_CFLAGS = \ GALLIUM_VIDEO_CFLAGS = \ -I$(top_srcdir)/include \ + -I$(top_srcdir)/src/loader \ -I$(top_srcdir)/src/gallium/include \ -I$(top_srcdir)/src/gallium/auxiliary \ -I$(top_srcdir)/src/gallium/drivers \ @@ -58,22 +59,6 @@ GALLIUM_DRI_LINKER_FLAGS = \ -avoid-version \ $(GC_SECTIONS) -GALLIUM_VDPAU_LINKER_FLAGS = \ - -shared \ - -module \ - -no-undefined \ - -version-number $(VDPAU_MAJOR):$(VDPAU_MINOR) \ - $(GC_SECTIONS) \ - $(LD_NO_UNDEFINED) - -GALLIUM_XVMC_LINKER_FLAGS = \ - -shared \ - -module \ - -no-undefined \ - -version-number $(XVMC_MAJOR):$(XVMC_MINOR) \ - $(GC_SECTIONS) \ - $(LD_NO_UNDEFINED) - GALLIUM_OMX_LINKER_FLAGS = \ -shared \ -module \ @@ -86,12 +71,6 @@ if HAVE_LD_VERSION_SCRIPT GALLIUM_DRI_LINKER_FLAGS += \ -Wl,--version-script=$(top_srcdir)/src/gallium/targets/dri.sym -GALLIUM_VDPAU_LINKER_FLAGS += \ - -Wl,--version-script=$(top_srcdir)/src/gallium/targets/vdpau.sym - -GALLIUM_XVMC_LINKER_FLAGS += \ - -Wl,--version-script=$(top_srcdir)/src/gallium/targets/xvmc.sym - GALLIUM_OMX_LINKER_FLAGS += \ -Wl,--version-script=$(top_srcdir)/src/gallium/targets/omx.sym endif @@ -111,20 +90,6 @@ GALLIUM_DRI_LIB_DEPS = \ $(EXPAT_LIBS) \ $(GALLIUM_COMMON_LIB_DEPS) -GALLIUM_VDPAU_LIB_DEPS = \ - $(top_builddir)/src/gallium/auxiliary/libgallium.la \ - $(top_builddir)/src/gallium/state_trackers/vdpau/libvdpautracker.la \ - $(VDPAU_LIBS) \ - $(LIBDRM_LIBS) \ - $(GALLIUM_COMMON_LIB_DEPS) - -GALLIUM_XVMC_LIB_DEPS = \ - $(top_builddir)/src/gallium/auxiliary/libgallium.la \ - $(top_builddir)/src/gallium/state_trackers/xvmc/libxvmctracker.la \ - $(XVMC_LIBS) \ - $(LIBDRM_LIBS) \ - $(GALLIUM_COMMON_LIB_DEPS) - GALLIUM_OMX_LIB_DEPS = \ $(top_builddir)/src/gallium/auxiliary/libgallium.la \ $(top_builddir)/src/gallium/state_trackers/omx/libomxtracker.la \ @@ -141,13 +106,25 @@ GALLIUM_WINSYS_CFLAGS = \ if HAVE_MESA_LLVM GALLIUM_DRI_LINKER_FLAGS += $(LLVM_LDFLAGS) -GALLIUM_VDPAU_LINKER_FLAGS += $(LLVM_LDFLAGS) -GALLIUM_XVMC_LINKER_FLAGS += $(LLVM_LDFLAGS) GALLIUM_OMX_LINKER_FLAGS += $(LLVM_LDFLAGS) GALLIUM_DRI_LIB_DEPS += $(LLVM_LIBS) -GALLIUM_VDPAU_LIB_DEPS += $(LLVM_LIBS) -GALLIUM_XVMC_LIB_DEPS += $(LLVM_LIBS) GALLIUM_OMX_LIB_DEPS += $(LLVM_LIBS) endif + + +GALLIUM_PIPE_LOADER_WINSYS_LIBS = \ + $(top_builddir)/src/gallium/winsys/sw/null/libws_null.la + +if HAVE_DRISW +GALLIUM_PIPE_LOADER_WINSYS_LIBS += \ + $(top_builddir)/src/gallium/winsys/sw/dri/libswdri.la +endif + +if NEED_WINSYS_XLIB +GALLIUM_PIPE_LOADER_WINSYS_LIBS += \ + $(top_builddir)/src/gallium/winsys/sw/xlib/libws_xlib.la \ + -lX11 -lXext -lXfixes \ + $(LIBDRM_LIBS) +endif diff --git a/mesalib/src/gallium/SConscript b/mesalib/src/gallium/SConscript index 32bbdbe56..598b2f1ec 100644 --- a/mesalib/src/gallium/SConscript +++ b/mesalib/src/gallium/SConscript @@ -21,12 +21,6 @@ SConscript([ 'drivers/trace/SConscript', ]) -if not env['msvc']: - # These drivers do not build on MSVC compilers - SConscript([ - 'drivers/i915/SConscript', - ]) - # # State trackers # @@ -66,11 +60,6 @@ if env['platform'] == 'windows': 'winsys/sw/gdi/SConscript', ]) -if not env['msvc']: - SConscript([ - 'winsys/i915/sw/SConscript', - ]) - if env['platform'] == 'haiku': SConscript([ 'winsys/sw/hgl/SConscript', @@ -85,11 +74,6 @@ if env['dri']: 'winsys/svga/drm/SConscript', ]) - if env['drm_intel']: - SConscript([ - 'winsys/i915/drm/SConscript', - ]) - # # Targets # @@ -126,10 +110,6 @@ if not env['embedded']: 'targets/dri-swrast/SConscript', 'targets/dri-vmwgfx/SConscript', ]) - if env['drm_intel']: - SConscript([ - 'targets/dri-i915/SConscript', - ]) # diff --git a/mesalib/src/gallium/auxiliary/util/u_format.c b/mesalib/src/gallium/auxiliary/util/u_format.c index 056f82f72..a53ed6f29 100644 --- a/mesalib/src/gallium/auxiliary/util/u_format.c +++ b/mesalib/src/gallium/auxiliary/util/u_format.c @@ -187,6 +187,17 @@ util_format_is_intensity(enum pipe_format format) return FALSE; } +boolean +util_format_is_subsampled_422(enum pipe_format format) +{ + const struct util_format_description *desc = + util_format_description(format); + + return desc->layout == UTIL_FORMAT_LAYOUT_SUBSAMPLED && + desc->block.width == 2 && + desc->block.height == 1 && + desc->block.bits == 32; +} boolean util_format_is_supported(enum pipe_format format, unsigned bind) diff --git a/mesalib/src/gallium/auxiliary/util/u_format.h b/mesalib/src/gallium/auxiliary/util/u_format.h index 1dd5d52f1..2e2bf0240 100644 --- a/mesalib/src/gallium/auxiliary/util/u_format.h +++ b/mesalib/src/gallium/auxiliary/util/u_format.h @@ -664,6 +664,9 @@ boolean util_format_is_intensity(enum pipe_format format); boolean +util_format_is_subsampled_422(enum pipe_format format); + +boolean util_format_is_pure_integer(enum pipe_format format); boolean diff --git a/mesalib/src/glsl/Makefile.sources b/mesalib/src/glsl/Makefile.sources index 5945590a5..b54eae72d 100644 --- a/mesalib/src/glsl/Makefile.sources +++ b/mesalib/src/glsl/Makefile.sources @@ -96,6 +96,7 @@ LIBGLSL_FILES = \ $(GLSL_SRCDIR)/opt_function_inlining.cpp \ $(GLSL_SRCDIR)/opt_if_simplification.cpp \ $(GLSL_SRCDIR)/opt_noop_swizzle.cpp \ + $(GLSL_SRCDIR)/opt_rebalance_tree.cpp \ $(GLSL_SRCDIR)/opt_redundant_jumps.cpp \ $(GLSL_SRCDIR)/opt_structure_splitting.cpp \ $(GLSL_SRCDIR)/opt_swizzle_swizzle.cpp \ diff --git a/mesalib/src/glsl/ast_to_hir.cpp b/mesalib/src/glsl/ast_to_hir.cpp index d1c77f1ec..7ba04a808 100644 --- a/mesalib/src/glsl/ast_to_hir.cpp +++ b/mesalib/src/glsl/ast_to_hir.cpp @@ -49,7 +49,6 @@ * parser (and lexer) sources. */ -#include "main/core.h" /* for struct gl_extensions */ #include "glsl_symbol_table.h" #include "glsl_parser_extras.h" #include "ast.h" @@ -2182,6 +2181,41 @@ validate_explicit_location(const struct ast_type_qualifier *qual, { bool fail = false; + /* Checks for GL_ARB_explicit_uniform_location. */ + if (qual->flags.q.uniform) { + if (!state->check_explicit_uniform_location_allowed(loc, var)) + return; + + const struct gl_context *const ctx = state->ctx; + unsigned max_loc = qual->location + var->type->uniform_locations() - 1; + + /* ARB_explicit_uniform_location specification states: + * + * "The explicitly defined locations and the generated locations + * must be in the range of 0 to MAX_UNIFORM_LOCATIONS minus one." + * + * "Valid locations for default-block uniform variable locations + * are in the range of 0 to the implementation-defined maximum + * number of uniform locations." + */ + if (qual->location < 0) { + _mesa_glsl_error(loc, state, + "explicit location < 0 for uniform %s", var->name); + return; + } + + if (max_loc >= ctx->Const.MaxUserAssignableUniformLocations) { + _mesa_glsl_error(loc, state, "location(s) consumed by uniform %s " + ">= MAX_UNIFORM_LOCATIONS (%u)", var->name, + ctx->Const.MaxUserAssignableUniformLocations); + return; + } + + var->data.explicit_location = true; + var->data.location = qual->location; + return; + } + /* Between GL_ARB_explicit_attrib_location an * GL_ARB_separate_shader_objects, the inputs and outputs of any shader * stage can be assigned explicit locations. The checking here associates @@ -2435,6 +2469,13 @@ apply_type_qualifier_to_variable(const struct ast_type_qualifier *qual, _mesa_shader_stage_to_string(state->stage)); } + /* Disallow layout qualifiers which may only appear on layout declarations. */ + if (qual->flags.q.prim_type) { + _mesa_glsl_error(loc, state, + "Primitive type may only be specified on GS input or output " + "layout declaration, not on variables."); + } + /* Section 6.1.1 (Function Calling Conventions) of the GLSL 1.10 spec says: * * "However, the const qualifier cannot be used with out or inout." @@ -2649,6 +2690,36 @@ apply_type_qualifier_to_variable(const struct ast_type_qualifier *qual, const bool uses_deprecated_qualifier = qual->flags.q.attribute || qual->flags.q.varying; + + /* Validate auxiliary storage qualifiers */ + + /* From section 4.3.4 of the GLSL 1.30 spec: + * "It is an error to use centroid in in a vertex shader." + * + * From section 4.3.4 of the GLSL ES 3.00 spec: + * "It is an error to use centroid in or interpolation qualifiers in + * a vertex shader input." + */ + + /* Section 4.3.6 of the GLSL 1.30 specification states: + * "It is an error to use centroid out in a fragment shader." + * + * The GL_ARB_shading_language_420pack extension specification states: + * "It is an error to use auxiliary storage qualifiers or interpolation + * qualifiers on an output in a fragment shader." + */ + if (qual->flags.q.sample && (!is_varying_var(var, state->stage) || uses_deprecated_qualifier)) { + _mesa_glsl_error(loc, state, + "sample qualifier may only be used on `in` or `out` " + "variables between shader stages"); + } + if (qual->flags.q.centroid && !is_varying_var(var, state->stage)) { + _mesa_glsl_error(loc, state, + "centroid qualifier may only be used with `in', " + "`out' or `varying' variables between shader stages"); + } + + /* Is the 'layout' keyword used with parameters that allow relaxed checking. * Many implementations of GL_ARB_fragment_coord_conventions_enable and some * implementations (only Mesa?) GL_ARB_explicit_attrib_location_enable @@ -3606,45 +3677,6 @@ ast_declarator_list::hir(exec_list *instructions, } - /* From section 4.3.4 of the GLSL 1.30 spec: - * "It is an error to use centroid in in a vertex shader." - * - * From section 4.3.4 of the GLSL ES 3.00 spec: - * "It is an error to use centroid in or interpolation qualifiers in - * a vertex shader input." - */ - if (state->is_version(130, 300) - && this->type->qualifier.flags.q.centroid - && this->type->qualifier.flags.q.in - && state->stage == MESA_SHADER_VERTEX) { - - _mesa_glsl_error(&loc, state, - "'centroid in' cannot be used in a vertex shader"); - } - - if (state->stage == MESA_SHADER_VERTEX - && this->type->qualifier.flags.q.sample - && this->type->qualifier.flags.q.in) { - - _mesa_glsl_error(&loc, state, - "'sample in' cannot be used in a vertex shader"); - } - - /* Section 4.3.6 of the GLSL 1.30 specification states: - * "It is an error to use centroid out in a fragment shader." - * - * The GL_ARB_shading_language_420pack extension specification states: - * "It is an error to use auxiliary storage qualifiers or interpolation - * qualifiers on an output in a fragment shader." - */ - if (state->stage == MESA_SHADER_FRAGMENT && - this->type->qualifier.flags.q.out && - this->type->qualifier.has_auxiliary_storage()) { - _mesa_glsl_error(&loc, state, - "auxiliary storage qualifiers cannot be used on " - "fragment shader outputs"); - } - /* Precision qualifiers exists only in GLSL versions 1.00 and >= 1.30. */ if (this->type->qualifier.precision != ast_precision_none) { @@ -4632,9 +4664,51 @@ ast_case_label::hir(exec_list *instructions, ir_dereference_variable *deref_test_var = new(ctx) ir_dereference_variable(state->switch_state.test_var); - ir_rvalue *const test_cond = new(ctx) ir_expression(ir_binop_all_equal, - label_const, - deref_test_var); + ir_expression *test_cond = new(ctx) ir_expression(ir_binop_all_equal, + label_const, + deref_test_var); + + /* + * From GLSL 4.40 specification section 6.2 ("Selection"): + * + * "The type of the init-expression value in a switch statement must + * be a scalar int or uint. The type of the constant-expression value + * in a case label also must be a scalar int or uint. When any pair + * of these values is tested for "equal value" and the types do not + * match, an implicit conversion will be done to convert the int to a + * uint (see section 4.1.10 “Implicit Conversions”) before the compare + * is done." + */ + if (label_const->type != state->switch_state.test_var->type) { + YYLTYPE loc = this->test_value->get_location(); + + const glsl_type *type_a = label_const->type; + const glsl_type *type_b = state->switch_state.test_var->type; + + /* Check if int->uint implicit conversion is supported. */ + bool integer_conversion_supported = + glsl_type::int_type->can_implicitly_convert_to(glsl_type::uint_type, + state); + + if ((!type_a->is_integer() || !type_b->is_integer()) || + !integer_conversion_supported) { + _mesa_glsl_error(&loc, state, "type mismatch with switch " + "init-expression and case label (%s != %s)", + type_a->name, type_b->name); + } else { + /* Conversion of the case label. */ + if (type_a->base_type == GLSL_TYPE_INT) { + if (!apply_implicit_conversion(glsl_type::uint_type, + test_cond->operands[0], state)) + _mesa_glsl_error(&loc, state, "implicit type conversion error"); + } else { + /* Conversion of the init-expression value. */ + if (!apply_implicit_conversion(glsl_type::uint_type, + test_cond->operands[1], state)) + _mesa_glsl_error(&loc, state, "implicit type conversion error"); + } + } + } ir_assignment *set_fallthru_on_test = new(ctx) ir_assignment(deref_fallthru_var, true_val, test_cond); @@ -5041,6 +5115,13 @@ ast_process_structure_or_interface_block(exec_list *instructions, "with uniform interface blocks"); } + if ((qual->flags.q.uniform || !is_interface) && + qual->has_auxiliary_storage()) { + _mesa_glsl_error(&loc, state, + "auxiliary storage qualifiers cannot be used " + "in uniform blocks or structures."); + } + if (field_type->is_matrix() || (field_type->is_array() && field_type->fields.array->is_matrix())) { fields[i].row_major = block_row_major; @@ -5090,7 +5171,7 @@ ast_struct_specifier::hir(exec_list *instructions, */ if (state->language_version != 110 && state->struct_specifier_depth != 0) _mesa_glsl_error(&loc, state, - "embedded structure declartions are not allowed"); + "embedded structure declarations are not allowed"); state->struct_specifier_depth++; @@ -5206,6 +5287,12 @@ ast_interface_block::hir(exec_list *instructions, bool block_row_major = this->layout.flags.q.row_major; exec_list declared_variables; glsl_struct_field *fields; + + /* Treat an interface block as one level of nesting, so that embedded struct + * specifiers will be disallowed. + */ + state->struct_specifier_depth++; + unsigned int num_variables = ast_process_structure_or_interface_block(&declared_variables, state, @@ -5217,6 +5304,8 @@ ast_interface_block::hir(exec_list *instructions, redeclaring_per_vertex, var_mode); + state->struct_specifier_depth--; + if (!redeclaring_per_vertex) validate_identifier(this->block_name, loc, state); diff --git a/mesalib/src/glsl/ast_type.cpp b/mesalib/src/glsl/ast_type.cpp index 0ee2c495a..77053d5b1 100644 --- a/mesalib/src/glsl/ast_type.cpp +++ b/mesalib/src/glsl/ast_type.cpp @@ -247,7 +247,7 @@ ast_type_qualifier::merge_in_qualifier(YYLTYPE *loc, q.flags.q.local_size != 0 && state->in_qualifier->flags.q.local_size == 0; - valid_in_mask.flags.q.local_size = 1; + valid_in_mask.flags.q.local_size = 7; break; default: _mesa_glsl_error(loc, state, diff --git a/mesalib/src/glsl/builtin_variables.cpp b/mesalib/src/glsl/builtin_variables.cpp index 9b35850ee..b9c69d23c 100644 --- a/mesalib/src/glsl/builtin_variables.cpp +++ b/mesalib/src/glsl/builtin_variables.cpp @@ -26,7 +26,6 @@ #include "glsl_symbol_table.h" #include "main/core.h" #include "main/uniforms.h" -#include "program/prog_parameter.h" #include "program/prog_statevars.h" #include "program/prog_instruction.h" @@ -939,6 +938,11 @@ builtin_variable_generator::generate_fs_special_vars() if (state->ARB_gpu_shader5_enable) { add_system_value(SYSTEM_VALUE_SAMPLE_MASK_IN, array(int_t, 1), "gl_SampleMaskIn"); } + + if (state->ARB_fragment_layer_viewport_enable) { + add_input(VARYING_SLOT_LAYER, int_t, "gl_Layer"); + add_input(VARYING_SLOT_VIEWPORT, int_t, "gl_ViewportIndex"); + } } diff --git a/mesalib/src/glsl/glcpp/glcpp-parse.y b/mesalib/src/glsl/glcpp/glcpp-parse.y index 98875837c..d8c395778 100644 --- a/mesalib/src/glsl/glcpp/glcpp-parse.y +++ b/mesalib/src/glsl/glcpp/glcpp-parse.y @@ -2086,9 +2086,15 @@ _glcpp_parser_handle_version_declaration(glcpp_parser_t *parser, intmax_t versio add_builtin_define(parser, "GL_ARB_fragment_coord_conventions", 1); + if (extensions->ARB_fragment_layer_viewport) + add_builtin_define(parser, "GL_ARB_fragment_layer_viewport", 1); + if (extensions->ARB_explicit_attrib_location) add_builtin_define(parser, "GL_ARB_explicit_attrib_location", 1); + if (extensions->ARB_explicit_uniform_location) + add_builtin_define(parser, "GL_ARB_explicit_uniform_location", 1); + if (extensions->ARB_shader_texture_lod) add_builtin_define(parser, "GL_ARB_shader_texture_lod", 1); diff --git a/mesalib/src/glsl/glsl_lexer.ll b/mesalib/src/glsl/glsl_lexer.ll index 6c3f9b692..db7b1d179 100644 --- a/mesalib/src/glsl/glsl_lexer.ll +++ b/mesalib/src/glsl/glsl_lexer.ll @@ -396,6 +396,7 @@ layout { || yyextra->AMD_conservative_depth_enable || yyextra->ARB_conservative_depth_enable || yyextra->ARB_explicit_attrib_location_enable + || yyextra->ARB_explicit_uniform_location_enable || yyextra->has_separate_shader_objects() || yyextra->ARB_uniform_buffer_object_enable || yyextra->ARB_fragment_coord_conventions_enable diff --git a/mesalib/src/glsl/glsl_parser.yy b/mesalib/src/glsl/glsl_parser.yy index b69802ddb..2b2de3047 100644 --- a/mesalib/src/glsl/glsl_parser.yy +++ b/mesalib/src/glsl/glsl_parser.yy @@ -1559,11 +1559,6 @@ type_qualifier: if ($2.flags.q.invariant) _mesa_glsl_error(&@1, state, "duplicate \"invariant\" qualifier"); - if ($2.has_layout()) { - _mesa_glsl_error(&@1, state, - "\"invariant\" cannot be used with layout(...)"); - } - if (!state->ARB_shading_language_420pack_enable && $2.flags.q.precise) _mesa_glsl_error(&@1, state, "\"invariant\" must come after \"precise\""); @@ -1586,11 +1581,6 @@ type_qualifier: if ($2.has_interpolation()) _mesa_glsl_error(&@1, state, "duplicate interpolation qualifier"); - if ($2.has_layout()) { - _mesa_glsl_error(&@1, state, "interpolation qualifiers cannot be used " - "with layout(...)"); - } - if (!state->ARB_shading_language_420pack_enable && ($2.flags.q.precise || $2.flags.q.invariant)) { _mesa_glsl_error(&@1, state, "interpolation qualifiers must come " @@ -1602,28 +1592,18 @@ type_qualifier: } | layout_qualifier type_qualifier { - /* The GLSL 1.50 grammar indicates that a layout(...) declaration can be - * used standalone or immediately before a storage qualifier. It cannot - * be used with interpolation qualifiers or invariant. There does not - * appear to be any text indicating that it must come before the storage - * qualifier, but always seems to in examples. + /* In the absence of ARB_shading_language_420pack, layout qualifiers may + * appear no later than auxiliary storage qualifiers. There is no + * particularly clear spec language mandating this, but in all examples + * the layout qualifier precedes the storage qualifier. + * + * We allow combinations of layout with interpolation, invariant or + * precise qualifiers since these are useful in ARB_separate_shader_objects. + * There is no clear spec guidance on this either. */ if (!state->ARB_shading_language_420pack_enable && $2.has_layout()) _mesa_glsl_error(&@1, state, "duplicate layout(...) qualifiers"); - if ($2.flags.q.invariant) - _mesa_glsl_error(&@1, state, "layout(...) cannot be used with " - "the \"invariant\" qualifier"); - - if ($2.flags.q.precise) - _mesa_glsl_error(&@1, state, "layout(...) cannot be used with " - "the \"precise\" qualifier"); - - if ($2.has_interpolation()) { - _mesa_glsl_error(&@1, state, "layout(...) cannot be used with " - "interpolation qualifiers"); - } - $$ = $1; $$.merge_qualifier(&@1, state, $2); } @@ -2181,7 +2161,7 @@ condition: ; /* - * siwtch_statement grammar is based on the syntax described in the body + * switch_statement grammar is based on the syntax described in the body * of the GLSL spec, not in it's appendix!!! */ switch_statement: diff --git a/mesalib/src/glsl/glsl_parser_extras.cpp b/mesalib/src/glsl/glsl_parser_extras.cpp index f3c5bd049..11a9a4320 100644 --- a/mesalib/src/glsl/glsl_parser_extras.cpp +++ b/mesalib/src/glsl/glsl_parser_extras.cpp @@ -515,7 +515,9 @@ static const _mesa_glsl_extension _mesa_glsl_supported_extensions[] = { EXT(ARB_draw_buffers, true, false, dummy_true), EXT(ARB_draw_instanced, true, false, ARB_draw_instanced), EXT(ARB_explicit_attrib_location, true, false, ARB_explicit_attrib_location), + EXT(ARB_explicit_uniform_location, true, false, ARB_explicit_uniform_location), EXT(ARB_fragment_coord_conventions, true, false, ARB_fragment_coord_conventions), + EXT(ARB_fragment_layer_viewport, true, false, ARB_fragment_layer_viewport), EXT(ARB_gpu_shader5, true, false, ARB_gpu_shader5), EXT(ARB_sample_shading, true, false, ARB_sample_shading), EXT(ARB_separate_shader_objects, true, false, dummy_true), @@ -1568,7 +1570,8 @@ do_common_optimization(exec_list *ir, bool linked, progress = do_constant_variable_unlinked(ir) || progress; progress = do_constant_folding(ir) || progress; progress = do_cse(ir) || progress; - progress = do_algebraic(ir, native_integers) || progress; + progress = do_rebalance_tree(ir) || progress; + progress = do_algebraic(ir, native_integers, options) || progress; progress = do_lower_jumps(ir) || progress; progress = do_vec_index_to_swizzle(ir) || progress; progress = lower_vector_insert(ir, false) || progress; diff --git a/mesalib/src/glsl/glsl_parser_extras.h b/mesalib/src/glsl/glsl_parser_extras.h index 49402fa21..2a5aea477 100644 --- a/mesalib/src/glsl/glsl_parser_extras.h +++ b/mesalib/src/glsl/glsl_parser_extras.h @@ -155,6 +155,21 @@ struct _mesa_glsl_parse_state { return true; } + bool check_explicit_uniform_location_allowed(YYLTYPE *locp, + const ir_variable *) + { + if (!this->has_explicit_attrib_location() || + !this->ARB_explicit_uniform_location_enable) { + _mesa_glsl_error(locp, this, + "uniform explicit location requires " + "GL_ARB_explicit_uniform_location and either " + "GL_ARB_explicit_attrib_location or GLSL 330."); + return false; + } + + return true; + } + bool has_explicit_attrib_location() const { return ARB_explicit_attrib_location_enable || is_version(330, 300); @@ -192,7 +207,7 @@ struct _mesa_glsl_parse_state { /** * Number of nested struct_specifier levels * - * Outside a struct_specifer, this is zero. + * Outside a struct_specifier, this is zero. */ unsigned struct_specifier_depth; @@ -367,8 +382,12 @@ struct _mesa_glsl_parse_state { bool ARB_draw_instanced_warn; bool ARB_explicit_attrib_location_enable; bool ARB_explicit_attrib_location_warn; + bool ARB_explicit_uniform_location_enable; + bool ARB_explicit_uniform_location_warn; bool ARB_fragment_coord_conventions_enable; bool ARB_fragment_coord_conventions_warn; + bool ARB_fragment_layer_viewport_enable; + bool ARB_fragment_layer_viewport_warn; bool ARB_gpu_shader5_enable; bool ARB_gpu_shader5_warn; bool ARB_sample_shading_enable; diff --git a/mesalib/src/glsl/glsl_symbol_table.h b/mesalib/src/glsl/glsl_symbol_table.h index 83d7935d8..db8863a20 100644 --- a/mesalib/src/glsl/glsl_symbol_table.h +++ b/mesalib/src/glsl/glsl_symbol_table.h @@ -32,9 +32,9 @@ extern "C" { #include "program/symbol_table.h" } #include "ir.h" -#include "glsl_types.h" class symbol_table_entry; +struct glsl_type; /** * Facade class for _mesa_symbol_table diff --git a/mesalib/src/glsl/glsl_types.cpp b/mesalib/src/glsl/glsl_types.cpp index e77146cdf..f9cd258fe 100644 --- a/mesalib/src/glsl/glsl_types.cpp +++ b/mesalib/src/glsl/glsl_types.cpp @@ -22,9 +22,7 @@ */ #include <stdio.h> -#include <stdlib.h> -#include "main/core.h" /* for Elements */ -#include "glsl_symbol_table.h" +#include "main/core.h" /* for Elements, MAX2 */ #include "glsl_parser_extras.h" #include "glsl_types.h" extern "C" { @@ -677,6 +675,32 @@ glsl_type::component_slots() const return 0; } +unsigned +glsl_type::uniform_locations() const +{ + if (this->is_matrix()) + return 1; + + unsigned size = 0; + + switch (this->base_type) { + case GLSL_TYPE_STRUCT: + case GLSL_TYPE_INTERFACE: + for (unsigned i = 0; i < this->length; i++) + size += this->fields.structure[i].type->uniform_locations(); + return size; + case GLSL_TYPE_ARRAY: + return this->length * this->fields.array->uniform_locations(); + default: + break; + } + + /* The location count for many types match with component_slots() result, + * all expections should be handled above. + */ + return component_slots(); +} + bool glsl_type::can_implicitly_convert_to(const glsl_type *desired, _mesa_glsl_parse_state *state) const diff --git a/mesalib/src/glsl/glsl_types.h b/mesalib/src/glsl/glsl_types.h index 35a4e6acc..f6d4a02ab 100644 --- a/mesalib/src/glsl/glsl_types.h +++ b/mesalib/src/glsl/glsl_types.h @@ -256,6 +256,12 @@ struct glsl_type { unsigned component_slots() const; /** + * Calculate the number of unique values from glGetUniformLocation for the + * elements of the type. + */ + unsigned uniform_locations() const; + + /** * Calculate the number of attribute slots required to hold this type * * This implements the language rules of GLSL 1.50 for counting the number diff --git a/mesalib/src/glsl/hir_field_selection.cpp b/mesalib/src/glsl/hir_field_selection.cpp index 1e92c89ae..0fa976811 100644 --- a/mesalib/src/glsl/hir_field_selection.cpp +++ b/mesalib/src/glsl/hir_field_selection.cpp @@ -22,7 +22,6 @@ */ #include "ir.h" -#include "program/symbol_table.h" #include "glsl_parser_extras.h" #include "ast.h" #include "glsl_types.h" diff --git a/mesalib/src/glsl/ir.cpp b/mesalib/src/glsl/ir.cpp index 2f4a0bec8..67dbac1eb 100644 --- a/mesalib/src/glsl/ir.cpp +++ b/mesalib/src/glsl/ir.cpp @@ -23,7 +23,6 @@ #include <string.h> #include "main/core.h" /* for MAX2 */ #include "ir.h" -#include "ir_visitor.h" #include "glsl_types.h" ir_rvalue::ir_rvalue(enum ir_node_type t) diff --git a/mesalib/src/glsl/ir_basic_block.cpp b/mesalib/src/glsl/ir_basic_block.cpp index 426fda2f2..74ee4b696 100644 --- a/mesalib/src/glsl/ir_basic_block.cpp +++ b/mesalib/src/glsl/ir_basic_block.cpp @@ -28,9 +28,7 @@ */ #include "ir.h" -#include "ir_visitor.h" #include "ir_basic_block.h" -#include "glsl_types.h" /** * Calls a user function for every basic block in the instruction stream. diff --git a/mesalib/src/glsl/ir_constant_expression.cpp b/mesalib/src/glsl/ir_constant_expression.cpp index f5cb12343..73380d243 100755 --- a/mesalib/src/glsl/ir_constant_expression.cpp +++ b/mesalib/src/glsl/ir_constant_expression.cpp @@ -36,7 +36,6 @@ #include <math.h> #include "main/core.h" /* for MAX2, MIN2, CLAMP */ #include "ir.h" -#include "ir_visitor.h" #include "glsl_types.h" #include "program/hash_table.h" diff --git a/mesalib/src/glsl/ir_expression_flattening.cpp b/mesalib/src/glsl/ir_expression_flattening.cpp index c1cadb122..0b1ada519 100644 --- a/mesalib/src/glsl/ir_expression_flattening.cpp +++ b/mesalib/src/glsl/ir_expression_flattening.cpp @@ -32,10 +32,8 @@ */ #include "ir.h" -#include "ir_visitor.h" #include "ir_rvalue_visitor.h" #include "ir_expression_flattening.h" -#include "glsl_types.h" class ir_expression_flattening_visitor : public ir_rvalue_visitor { public: diff --git a/mesalib/src/glsl/ir_optimization.h b/mesalib/src/glsl/ir_optimization.h index c63921c26..b83c22592 100644 --- a/mesalib/src/glsl/ir_optimization.h +++ b/mesalib/src/glsl/ir_optimization.h @@ -71,7 +71,9 @@ bool do_common_optimization(exec_list *ir, bool linked, const struct gl_shader_compiler_options *options, bool native_integers); -bool do_algebraic(exec_list *instructions, bool native_integers); +bool do_rebalance_tree(exec_list *instructions); +bool do_algebraic(exec_list *instructions, bool native_integers, + const struct gl_shader_compiler_options *options); bool do_constant_folding(exec_list *instructions); bool do_constant_variable(exec_list *instructions); bool do_constant_variable_unlinked(exec_list *instructions); diff --git a/mesalib/src/glsl/ir_uniform.h b/mesalib/src/glsl/ir_uniform.h index 3508509d4..2f7352825 100644 --- a/mesalib/src/glsl/ir_uniform.h +++ b/mesalib/src/glsl/ir_uniform.h @@ -32,12 +32,17 @@ #include "program/prog_parameter.h" /* For union gl_constant_value. */ +/** + * Used by GL_ARB_explicit_uniform_location extension code in the linker + * and glUniform* functions to identify inactive explicit uniform locations. + */ +#define INACTIVE_UNIFORM_EXPLICIT_LOCATION ((gl_uniform_storage *) -1) #ifdef __cplusplus extern "C" { #endif -enum gl_uniform_driver_format { +enum PACKED gl_uniform_driver_format { uniform_native = 0, /**< Store data in the native format. */ uniform_int_float, /**< Store integer data as floats. */ uniform_bool_float, /**< Store boolean data as floats. */ @@ -66,11 +71,8 @@ struct gl_uniform_driver_storage { /** * Base format of the stored data. - * - * This field must have a value from \c GLSL_TYPE_UINT through \c - * GLSL_TYPE_SAMPLER. */ - uint8_t format; + enum gl_uniform_driver_format format; /** * Pointer to the base of the data. diff --git a/mesalib/src/glsl/link_uniform_block_active_visitor.h b/mesalib/src/glsl/link_uniform_block_active_visitor.h index d76dbcaf1..524cd6b91 100644 --- a/mesalib/src/glsl/link_uniform_block_active_visitor.h +++ b/mesalib/src/glsl/link_uniform_block_active_visitor.h @@ -26,8 +26,6 @@ #define LINK_UNIFORM_BLOCK_ACTIVE_VISITOR_H #include "ir.h" -#include "ir_visitor.h" -#include "glsl_types.h" #include "main/hash_table.h" struct link_uniform_block_active { diff --git a/mesalib/src/glsl/link_uniform_initializers.cpp b/mesalib/src/glsl/link_uniform_initializers.cpp index 2100e0517..d755cec98 100644 --- a/mesalib/src/glsl/link_uniform_initializers.cpp +++ b/mesalib/src/glsl/link_uniform_initializers.cpp @@ -25,8 +25,6 @@ #include "ir.h" #include "linker.h" #include "ir_uniform.h" -#include "glsl_symbol_table.h" -#include "program/hash_table.h" /* These functions are put in a "private" namespace instead of being marked * static so that the unit tests can access them. See diff --git a/mesalib/src/glsl/link_uniforms.cpp b/mesalib/src/glsl/link_uniforms.cpp index 377fed64a..5dcb7b571 100644 --- a/mesalib/src/glsl/link_uniforms.cpp +++ b/mesalib/src/glsl/link_uniforms.cpp @@ -37,6 +37,11 @@ */ /** + * Used by linker to indicate uniforms that have no location set. + */ +#define UNMAPPED_UNIFORM_LOC ~0u + +/** * Count the backing storage requirements for a type */ static unsigned @@ -386,6 +391,9 @@ public: void set_and_process(struct gl_shader_program *prog, ir_variable *var) { + current_var = var; + field_counter = 0; + ubo_block_index = -1; if (var->is_in_uniform_block()) { if (var->is_interface_instance() && var->type->is_array()) { @@ -542,6 +550,22 @@ private: return; } + /* Assign explicit locations. */ + if (current_var->data.explicit_location) { + /* Set sequential locations for struct fields. */ + if (record_type != NULL) { + const unsigned entries = MAX2(1, this->uniforms[id].array_elements); + this->uniforms[id].remap_location = + current_var->data.location + field_counter; + field_counter += entries; + } else { + this->uniforms[id].remap_location = current_var->data.location; + } + } else { + /* Initialize to to indicate that no location is set */ + this->uniforms[id].remap_location = UNMAPPED_UNIFORM_LOC; + } + this->uniforms[id].name = ralloc_strdup(this->uniforms, name); this->uniforms[id].type = base_type; this->uniforms[id].initialized = 0; @@ -597,6 +621,17 @@ public: gl_texture_index targets[MAX_SAMPLERS]; /** + * Current variable being processed. + */ + ir_variable *current_var; + + /** + * Field counter is used to take care that uniform structures + * with explicit locations get sequential locations. + */ + unsigned field_counter; + + /** * Mask of samplers used by the current shader stage. */ unsigned shader_samplers_used; @@ -798,10 +833,6 @@ link_assign_uniform_locations(struct gl_shader_program *prog) prog->UniformStorage = NULL; prog->NumUserUniformStorage = 0; - ralloc_free(prog->UniformRemapTable); - prog->UniformRemapTable = NULL; - prog->NumUniformRemapTable = 0; - if (prog->UniformHash != NULL) { prog->UniformHash->clear(); } else { @@ -914,8 +945,28 @@ link_assign_uniform_locations(struct gl_shader_program *prog) sizeof(prog->_LinkedShaders[i]->SamplerTargets)); } - /* Build the uniform remap table that is used to set/get uniform locations */ + /* Reserve all the explicit locations of the active uniforms. */ for (unsigned i = 0; i < num_user_uniforms; i++) { + if (uniforms[i].remap_location != UNMAPPED_UNIFORM_LOC) { + /* How many new entries for this uniform? */ + const unsigned entries = MAX2(1, uniforms[i].array_elements); + + /* Set remap table entries point to correct gl_uniform_storage. */ + for (unsigned j = 0; j < entries; j++) { + unsigned element_loc = uniforms[i].remap_location + j; + assert(prog->UniformRemapTable[element_loc] == + INACTIVE_UNIFORM_EXPLICIT_LOCATION); + prog->UniformRemapTable[element_loc] = &uniforms[i]; + } + } + } + + /* Reserve locations for rest of the uniforms. */ + for (unsigned i = 0; i < num_user_uniforms; i++) { + + /* Explicit ones have been set already. */ + if (uniforms[i].remap_location != UNMAPPED_UNIFORM_LOC) + continue; /* how many new entries for this uniform? */ const unsigned entries = MAX2(1, uniforms[i].array_elements); diff --git a/mesalib/src/glsl/linker.cpp b/mesalib/src/glsl/linker.cpp index a43d23082..0b6a71679 100644 --- a/mesalib/src/glsl/linker.cpp +++ b/mesalib/src/glsl/linker.cpp @@ -74,6 +74,7 @@ #include "link_varyings.h" #include "ir_optimization.h" #include "ir_rvalue_visitor.h" +#include "ir_uniform.h" extern "C" { #include "main/shaderobj.h" @@ -2224,6 +2225,115 @@ check_image_resources(struct gl_context *ctx, struct gl_shader_program *prog) linker_error(prog, "Too many combined image uniforms and fragment outputs"); } + +/** + * Initializes explicit location slots to INACTIVE_UNIFORM_EXPLICIT_LOCATION + * for a variable, checks for overlaps between other uniforms using explicit + * locations. + */ +static bool +reserve_explicit_locations(struct gl_shader_program *prog, + string_to_uint_map *map, ir_variable *var) +{ + unsigned slots = var->type->uniform_locations(); + unsigned max_loc = var->data.location + slots - 1; + + /* Resize remap table if locations do not fit in the current one. */ + if (max_loc + 1 > prog->NumUniformRemapTable) { + prog->UniformRemapTable = + reralloc(prog, prog->UniformRemapTable, + gl_uniform_storage *, + max_loc + 1); + + if (!prog->UniformRemapTable) { + linker_error(prog, "Out of memory during linking."); + return false; + } + + /* Initialize allocated space. */ + for (unsigned i = prog->NumUniformRemapTable; i < max_loc + 1; i++) + prog->UniformRemapTable[i] = NULL; + + prog->NumUniformRemapTable = max_loc + 1; + } + + for (unsigned i = 0; i < slots; i++) { + unsigned loc = var->data.location + i; + + /* Check if location is already used. */ + if (prog->UniformRemapTable[loc] == INACTIVE_UNIFORM_EXPLICIT_LOCATION) { + + /* Possibly same uniform from a different stage, this is ok. */ + unsigned hash_loc; + if (map->get(hash_loc, var->name) && hash_loc == loc - i) + continue; + + /* ARB_explicit_uniform_location specification states: + * + * "No two default-block uniform variables in the program can have + * the same location, even if they are unused, otherwise a compiler + * or linker error will be generated." + */ + linker_error(prog, + "location qualifier for uniform %s overlaps" + "previously used location", + var->name); + return false; + } + + /* Initialize location as inactive before optimization + * rounds and location assignment. + */ + prog->UniformRemapTable[loc] = INACTIVE_UNIFORM_EXPLICIT_LOCATION; + } + + /* Note, base location used for arrays. */ + map->put(var->data.location, var->name); + + return true; +} + +/** + * Check and reserve all explicit uniform locations, called before + * any optimizations happen to handle also inactive uniforms and + * inactive array elements that may get trimmed away. + */ +static void +check_explicit_uniform_locations(struct gl_context *ctx, + struct gl_shader_program *prog) +{ + if (!ctx->Extensions.ARB_explicit_uniform_location) + return; + + /* This map is used to detect if overlapping explicit locations + * occur with the same uniform (from different stage) or a different one. + */ + string_to_uint_map *uniform_map = new string_to_uint_map; + + if (!uniform_map) { + linker_error(prog, "Out of memory during linking."); + return; + } + + for (unsigned i = 0; i < MESA_SHADER_STAGES; i++) { + struct gl_shader *sh = prog->_LinkedShaders[i]; + + if (!sh) + continue; + + foreach_list(node, sh->ir) { + ir_variable *var = ((ir_instruction *)node)->as_variable(); + if ((var && var->data.mode == ir_var_uniform) && + var->data.explicit_location) { + if (!reserve_explicit_locations(prog, uniform_map, var)) + return; + } + } + } + + delete uniform_map; +} + void link_shaders(struct gl_context *ctx, struct gl_shader_program *prog) { @@ -2372,6 +2482,10 @@ link_shaders(struct gl_context *ctx, struct gl_shader_program *prog) break; } + check_explicit_uniform_locations(ctx, prog); + if (!prog->LinkStatus) + goto done; + /* Validate the inputs of each stage with the output of the preceding * stage. */ diff --git a/mesalib/src/glsl/list.h b/mesalib/src/glsl/list.h index b2e249657..fa6ec12cc 100644 --- a/mesalib/src/glsl/list.h +++ b/mesalib/src/glsl/list.h @@ -87,67 +87,29 @@ struct exec_node { /* empty */ } - const exec_node *get_next() const - { - return next; - } + const exec_node *get_next() const; + exec_node *get_next(); - exec_node *get_next() - { - return next; - } + const exec_node *get_prev() const; + exec_node *get_prev(); - const exec_node *get_prev() const - { - return prev; - } - - exec_node *get_prev() - { - return prev; - } - - void remove() - { - next->prev = prev; - prev->next = next; - next = NULL; - prev = NULL; - } + void remove(); /** * Link a node with itself * * This creates a sort of degenerate list that is occasionally useful. */ - void self_link() - { - next = this; - prev = this; - } + void self_link(); /** * Insert a node in the list after the current node */ - void insert_after(exec_node *after) - { - after->next = this->next; - after->prev = this; - - this->next->prev = after; - this->next = after; - } + void insert_after(exec_node *after); /** * Insert a node in the list before the current node */ - void insert_before(exec_node *before) - { - before->next = this; - before->prev = this->prev; - - this->prev->next = before; - this->prev = before; - } + void insert_before(exec_node *before); /** * Insert another list in the list before the current node @@ -157,33 +119,165 @@ struct exec_node { /** * Replace the current node with the given node. */ - void replace_with(exec_node *replacement) - { - replacement->prev = this->prev; - replacement->next = this->next; - - this->prev->next = replacement; - this->next->prev = replacement; - } + void replace_with(exec_node *replacement); /** * Is this the sentinel at the tail of the list? */ - bool is_tail_sentinel() const - { - return this->next == NULL; - } + bool is_tail_sentinel() const; /** * Is this the sentinel at the head of the list? */ - bool is_head_sentinel() const - { - return this->prev == NULL; - } + bool is_head_sentinel() const; #endif }; +static inline void +exec_node_init(struct exec_node *n) +{ + n->next = NULL; + n->prev = NULL; +} + +static inline const struct exec_node * +exec_node_get_next_const(const struct exec_node *n) +{ + return n->next; +} + +static inline struct exec_node * +exec_node_get_next(struct exec_node *n) +{ + return n->next; +} + +static inline const struct exec_node * +exec_node_get_prev_const(const struct exec_node *n) +{ + return n->prev; +} + +static inline struct exec_node * +exec_node_get_prev(struct exec_node *n) +{ + return n->prev; +} + +static inline void +exec_node_remove(struct exec_node *n) +{ + n->next->prev = n->prev; + n->prev->next = n->next; + n->next = NULL; + n->prev = NULL; +} + +static inline void +exec_node_self_link(struct exec_node *n) +{ + n->next = n; + n->prev = n; +} + +static inline void +exec_node_insert_after(struct exec_node *n, struct exec_node *after) +{ + after->next = n->next; + after->prev = n; + + n->next->prev = after; + n->next = after; +} + +static inline void +exec_node_insert_node_before(struct exec_node *n, struct exec_node *before) +{ + before->next = n; + before->prev = n->prev; + + n->prev->next = before; + n->prev = before; +} + +static inline void +exec_node_replace_with(struct exec_node *n, struct exec_node *replacement) +{ + replacement->prev = n->prev; + replacement->next = n->next; + + n->prev->next = replacement; + n->next->prev = replacement; +} + +static inline bool +exec_node_is_tail_sentinel(const struct exec_node *n) +{ + return n->next == NULL; +} + +static inline bool +exec_node_is_head_sentinel(const struct exec_node *n) +{ + return n->prev == NULL; +} + +#ifdef __cplusplus +inline const exec_node *exec_node::get_next() const +{ + return exec_node_get_next_const(this); +} + +inline exec_node *exec_node::get_next() +{ + return exec_node_get_next(this); +} + +inline const exec_node *exec_node::get_prev() const +{ + return exec_node_get_prev_const(this); +} + +inline exec_node *exec_node::get_prev() +{ + return exec_node_get_prev(this); +} + +inline void exec_node::remove() +{ + exec_node_remove(this); +} + +inline void exec_node::self_link() +{ + exec_node_self_link(this); +} + +inline void exec_node::insert_after(exec_node *after) +{ + exec_node_insert_after(this, after); +} + +inline void exec_node::insert_before(exec_node *before) +{ + exec_node_insert_node_before(this, before); +} + +inline void exec_node::replace_with(exec_node *replacement) +{ + exec_node_replace_with(this, replacement); +} + +inline bool exec_node::is_tail_sentinel() const +{ + return exec_node_is_tail_sentinel(this); +} + +inline bool exec_node::is_head_sentinel() const +{ + return exec_node_is_head_sentinel(this); +} +#endif #ifdef __cplusplus /* This macro will not work correctly if `t' uses virtual inheritance. If you @@ -229,75 +323,19 @@ struct exec_list { make_empty(); } - void make_empty() - { - head = (exec_node *) & tail; - tail = NULL; - tail_pred = (exec_node *) & head; - } - - bool is_empty() const - { - /* There are three ways to test whether a list is empty or not. - * - * - Check to see if the \c head points to the \c tail. - * - Check to see if the \c tail_pred points to the \c head. - * - Check to see if the \c head is the sentinel node by test whether its - * \c next pointer is \c NULL. - * - * The first two methods tend to generate better code on modern systems - * because they save a pointer dereference. - */ - return head == (exec_node *) &tail; - } - - const exec_node *get_head() const - { - return !is_empty() ? head : NULL; - } - - exec_node *get_head() - { - return !is_empty() ? head : NULL; - } - - const exec_node *get_tail() const - { - return !is_empty() ? tail_pred : NULL; - } - - exec_node *get_tail() - { - return !is_empty() ? tail_pred : NULL; - } + void make_empty(); - void push_head(exec_node *n) - { - n->next = head; - n->prev = (exec_node *) &head; + bool is_empty() const; - n->next->prev = n; - head = n; - } + const exec_node *get_head() const; + exec_node *get_head(); - void push_tail(exec_node *n) - { - n->next = (exec_node *) &tail; - n->prev = tail_pred; + const exec_node *get_tail() const; + exec_node *get_tail(); - n->prev->next = n; - tail_pred = n; - } - - void push_degenerate_list_at_head(exec_node *n) - { - assert(n->prev->next == n); - - n->prev->next = head; - head->prev = n->prev; - n->prev = (exec_node *) &head; - head = n; - } + void push_head(exec_node *n); + void push_tail(exec_node *n); + void push_degenerate_list_at_head(exec_node *n); /** * Remove the first node from a list and return it @@ -307,87 +345,239 @@ struct exec_list { * * \sa exec_list::get_head */ - exec_node *pop_head() - { - exec_node *const n = this->get_head(); - if (n != NULL) - n->remove(); - - return n; - } + exec_node *pop_head(); /** * Move all of the nodes from this list to the target list */ - void move_nodes_to(exec_list *target) - { - if (is_empty()) { - target->make_empty(); - } else { - target->head = head; - target->tail = NULL; - target->tail_pred = tail_pred; - - target->head->prev = (exec_node *) &target->head; - target->tail_pred->next = (exec_node *) &target->tail; - - make_empty(); - } - } + void move_nodes_to(exec_list *target); /** * Append all nodes from the source list to the target list */ - void - append_list(exec_list *source) - { - if (source->is_empty()) - return; - - /* Link the first node of the source with the last node of the target list. - */ - this->tail_pred->next = source->head; - source->head->prev = this->tail_pred; - - /* Make the tail of the source list be the tail of the target list. - */ - this->tail_pred = source->tail_pred; - this->tail_pred->next = (exec_node *) &this->tail; - - /* Make the source list empty for good measure. - */ - source->make_empty(); - } + void append_list(exec_list *source); #endif }; +static inline void +exec_list_make_empty(struct exec_list *list) +{ + list->head = (struct exec_node *) & list->tail; + list->tail = NULL; + list->tail_pred = (struct exec_node *) & list->head; +} -#ifdef __cplusplus -inline void exec_node::insert_before(exec_list *before) +static inline bool +exec_list_is_empty(const struct exec_list *list) +{ + /* There are three ways to test whether a list is empty or not. + * + * - Check to see if the \c head points to the \c tail. + * - Check to see if the \c tail_pred points to the \c head. + * - Check to see if the \c head is the sentinel node by test whether its + * \c next pointer is \c NULL. + * + * The first two methods tend to generate better code on modern systems + * because they save a pointer dereference. + */ + return list->head == (struct exec_node *) &list->tail; +} + +static inline const struct exec_node * +exec_list_get_head_const(const struct exec_list *list) +{ + return !exec_list_is_empty(list) ? list->head : NULL; +} + +static inline struct exec_node * +exec_list_get_head(struct exec_list *list) +{ + return !exec_list_is_empty(list) ? list->head : NULL; +} + +static inline const struct exec_node * +exec_list_get_tail_const(const struct exec_list *list) +{ + return !exec_list_is_empty(list) ? list->tail_pred : NULL; +} + +static inline struct exec_node * +exec_list_get_tail(struct exec_list *list) +{ + return !exec_list_is_empty(list) ? list->tail_pred : NULL; +} + +static inline void +exec_list_push_head(struct exec_list *list, struct exec_node *n) +{ + n->next = list->head; + n->prev = (struct exec_node *) &list->head; + + n->next->prev = n; + list->head = n; +} + +static inline void +exec_list_push_tail(struct exec_list *list, struct exec_node *n) +{ + n->next = (struct exec_node *) &list->tail; + n->prev = list->tail_pred; + + n->prev->next = n; + list->tail_pred = n; +} + +static inline void +exec_list_push_degenerate_list_at_head(struct exec_list *list, struct exec_node *n) +{ + assert(n->prev->next == n); + + n->prev->next = list->head; + list->head->prev = n->prev; + n->prev = (struct exec_node *) &list->head; + list->head = n; +} + +static inline struct exec_node * +exec_list_pop_head(struct exec_list *list) +{ + struct exec_node *const n = exec_list_get_head(list); + if (n != NULL) + exec_node_remove(n); + + return n; +} + +static inline void +exec_list_move_nodes_to(struct exec_list *list, struct exec_list *target) +{ + if (exec_list_is_empty(list)) { + exec_list_make_empty(target); + } else { + target->head = list->head; + target->tail = NULL; + target->tail_pred = list->tail_pred; + + target->head->prev = (struct exec_node *) &target->head; + target->tail_pred->next = (struct exec_node *) &target->tail; + + exec_list_make_empty(list); + } +} + +static inline void +exec_list_append(struct exec_list *list, struct exec_list *source) +{ + if (exec_list_is_empty(source)) + return; + + /* Link the first node of the source with the last node of the target list. + */ + list->tail_pred->next = source->head; + source->head->prev = list->tail_pred; + + /* Make the tail of the source list be the tail of the target list. + */ + list->tail_pred = source->tail_pred; + list->tail_pred->next = (struct exec_node *) &list->tail; + + /* Make the source list empty for good measure. + */ + exec_list_make_empty(source); +} + +static inline void +exec_node_insert_list_before(struct exec_node *n, struct exec_list *before) { - if (before->is_empty()) + if (exec_list_is_empty(before)) return; - before->tail_pred->next = this; - before->head->prev = this->prev; + before->tail_pred->next = n; + before->head->prev = n->prev; - this->prev->next = before->head; - this->prev = before->tail_pred; + n->prev->next = before->head; + n->prev = before->tail_pred; - before->make_empty(); + exec_list_make_empty(before); +} + +#ifdef __cplusplus +inline void exec_list::make_empty() +{ + exec_list_make_empty(this); +} + +inline bool exec_list::is_empty() const +{ + return exec_list_is_empty(this); +} + +inline const exec_node *exec_list::get_head() const +{ + return exec_list_get_head_const(this); +} + +inline exec_node *exec_list::get_head() +{ + return exec_list_get_head(this); +} + +inline const exec_node *exec_list::get_tail() const +{ + return exec_list_get_tail_const(this); +} + +inline exec_node *exec_list::get_tail() +{ + return exec_list_get_tail(this); +} + +inline void exec_list::push_head(exec_node *n) +{ + exec_list_push_head(this, n); +} + +inline void exec_list::push_tail(exec_node *n) +{ + exec_list_push_tail(this, n); +} + +inline void exec_list::push_degenerate_list_at_head(exec_node *n) +{ + exec_list_push_degenerate_list_at_head(this, n); +} + +inline exec_node *exec_list::pop_head() +{ + return exec_list_pop_head(this); +} + +inline void exec_list::move_nodes_to(exec_list *target) +{ + exec_list_move_nodes_to(this, target); +} + +inline void exec_list::append_list(exec_list *source) +{ + exec_list_append(this, source); +} + +inline void exec_node::insert_before(exec_list *before) +{ + exec_node_insert_list_before(this, before); } #endif /** * This version is safe even if the current node is removed. */ -#define foreach_list_safe(__node, __list) \ - for (exec_node * __node = (__list)->head, * __next = __node->next \ - ; __next != NULL \ +#define foreach_list_safe(__node, __list) \ + for (struct exec_node * __node = (__list)->head, * __next = __node->next \ + ; __next != NULL \ ; __node = __next, __next = __next->next) #define foreach_list(__node, __list) \ - for (exec_node * __node = (__list)->head \ + for (struct exec_node * __node = (__list)->head \ ; (__node)->next != NULL \ ; (__node) = (__node)->next) @@ -397,19 +587,19 @@ inline void exec_node::insert_before(exec_list *before) * This is safe against either current node being removed or replaced. */ #define foreach_two_lists(__node1, __list1, __node2, __list2) \ - for (exec_node * __node1 = (__list1)->head, \ - * __node2 = (__list2)->head, \ - * __next1 = __node1->next, \ - * __next2 = __node2->next \ + for (struct exec_node * __node1 = (__list1)->head, \ + * __node2 = (__list2)->head, \ + * __next1 = __node1->next, \ + * __next2 = __node2->next \ ; __next1 != NULL && __next2 != NULL \ ; __node1 = __next1, \ __node2 = __next2, \ __next1 = __next1->next, \ __next2 = __next2->next) -#define foreach_list_const(__node, __list) \ - for (const exec_node * __node = (__list)->head \ - ; (__node)->next != NULL \ +#define foreach_list_const(__node, __list) \ + for (const struct exec_node * __node = (__list)->head \ + ; (__node)->next != NULL \ ; (__node) = (__node)->next) #define foreach_list_typed(__type, __node, __field, __list) \ diff --git a/mesalib/src/glsl/opt_algebraic.cpp b/mesalib/src/glsl/opt_algebraic.cpp index 9d5539252..ac7514acf 100644 --- a/mesalib/src/glsl/opt_algebraic.cpp +++ b/mesalib/src/glsl/opt_algebraic.cpp @@ -45,7 +45,9 @@ namespace { class ir_algebraic_visitor : public ir_rvalue_visitor { public: - ir_algebraic_visitor(bool native_integers) + ir_algebraic_visitor(bool native_integers, + const struct gl_shader_compiler_options *options) + : options(options) { this->progress = false; this->mem_ctx = NULL; @@ -69,6 +71,7 @@ public: ir_rvalue *swizzle_if_required(ir_expression *expr, ir_rvalue *operand); + const struct gl_shader_compiler_options *options; void *mem_ctx; bool native_integers; @@ -116,6 +119,46 @@ update_type(ir_expression *ir) ir->type = ir->operands[1]->type; } +/* Recognize (v.x + v.y) + (v.z + v.w) as dot(v, 1.0) */ +static ir_expression * +try_replace_with_dot(ir_expression *expr0, ir_expression *expr1, void *mem_ctx) +{ + if (expr0 && expr0->operation == ir_binop_add && + expr0->type->is_float() && + expr1 && expr1->operation == ir_binop_add && + expr1->type->is_float()) { + ir_swizzle *x = expr0->operands[0]->as_swizzle(); + ir_swizzle *y = expr0->operands[1]->as_swizzle(); + ir_swizzle *z = expr1->operands[0]->as_swizzle(); + ir_swizzle *w = expr1->operands[1]->as_swizzle(); + + if (!x || x->mask.num_components != 1 || + !y || y->mask.num_components != 1 || + !z || z->mask.num_components != 1 || + !w || w->mask.num_components != 1) { + return NULL; + } + + bool swiz_seen[4] = {false, false, false, false}; + swiz_seen[x->mask.x] = true; + swiz_seen[y->mask.x] = true; + swiz_seen[z->mask.x] = true; + swiz_seen[w->mask.x] = true; + + if (!swiz_seen[0] || !swiz_seen[1] || + !swiz_seen[2] || !swiz_seen[3]) { + return NULL; + } + + if (x->val->equals(y->val) && + x->val->equals(z->val) && + x->val->equals(w->val)) { + return dot(x->val, new(mem_ctx) ir_constant(1.0f, 4)); + } + } + return NULL; +} + void ir_algebraic_visitor::reassociate_operands(ir_expression *ir1, int op1, @@ -329,6 +372,14 @@ ir_algebraic_visitor::handle_expression(ir_expression *ir) if (op_const[1] && !op_const[0]) reassociate_constant(ir, 1, op_const[1], op_expr[0]); + /* Recognize (v.x + v.y) + (v.z + v.w) as dot(v, 1.0) */ + if (options->OptimizeForAOS) { + ir_expression *expr = try_replace_with_dot(op_expr[0], op_expr[1], + mem_ctx); + if (expr) + return expr; + } + /* Replace (-x + y) * a + x and commutative variations with lrp(x, y, a). * * (-x + y) * a + x @@ -380,6 +431,7 @@ ir_algebraic_visitor::handle_expression(ir_expression *ir) } } } + break; case ir_binop_sub: @@ -647,9 +699,10 @@ ir_algebraic_visitor::handle_rvalue(ir_rvalue **rvalue) } bool -do_algebraic(exec_list *instructions, bool native_integers) +do_algebraic(exec_list *instructions, bool native_integers, + const struct gl_shader_compiler_options *options) { - ir_algebraic_visitor v(native_integers); + ir_algebraic_visitor v(native_integers, options); visit_list_elements(&v, instructions); diff --git a/mesalib/src/glsl/opt_dead_builtin_varyings.cpp b/mesalib/src/glsl/opt_dead_builtin_varyings.cpp index 6612592aa..50c8aa763 100644 --- a/mesalib/src/glsl/opt_dead_builtin_varyings.cpp +++ b/mesalib/src/glsl/opt_dead_builtin_varyings.cpp @@ -334,7 +334,7 @@ public: } void prepare_array(exec_list *ir, - struct ir_variable **new_var, + ir_variable **new_var, int max_elements, unsigned start_location, const char *var_name, const char *mode_str, unsigned usage, unsigned external_usage) diff --git a/mesalib/src/glsl/opt_rebalance_tree.cpp b/mesalib/src/glsl/opt_rebalance_tree.cpp new file mode 100644 index 000000000..773aab3f6 --- /dev/null +++ b/mesalib/src/glsl/opt_rebalance_tree.cpp @@ -0,0 +1,300 @@ +/* + * Copyright © 2014 Intel Corporation + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice (including the next + * paragraph) shall be included in all copies or substantial portions of the + * Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + +/** + * \file opt_rebalance_tree.cpp + * + * Rebalances a reduction expression tree. + * + * For reduction operations (e.g., x + y + z + w) we generate an expression + * tree like + * + * + + * / \ + * + w + * / \ + * + z + * / \ + * x y + * + * which we can rebalance into + * + * + + * / \ + * / \ + * + + + * / \ / \ + * x y z w + * + * to get a better instruction scheduling. + * + * See "Tree Rebalancing in Optimal Editor Time and Space" by Quentin F. Stout + * and Bette L. Warren. + * + * Also see http://penguin.ewu.edu/~trolfe/DSWpaper/ for a very readable + * explanation of the of the tree_to_vine() (rightward rotation) and + * vine_to_tree() (leftward rotation) algorithms. + */ + +#include "ir.h" +#include "ir_visitor.h" +#include "ir_rvalue_visitor.h" +#include "ir_optimization.h" + +/* The DSW algorithm generates a degenerate tree (really, a linked list) in + * tree_to_vine(). We'd rather not leave a binary expression with only one + * operand, so trivial modifications (the ternary operators below) are needed + * to ensure that we only rotate around the ir_expression nodes of the tree. + */ +static unsigned +tree_to_vine(ir_expression *root) +{ + unsigned size = 0; + ir_rvalue *vine_tail = root; + ir_rvalue *remainder = root->operands[1]; + + while (remainder != NULL) { + ir_expression *remainder_temp = remainder->as_expression(); + ir_expression *remainder_left = remainder_temp ? + remainder_temp->operands[0]->as_expression() : NULL; + + if (remainder_left == NULL) { + /* move vine_tail down one */ + vine_tail = remainder; + remainder = remainder->as_expression() ? + ((ir_expression *)remainder)->operands[1] : NULL; + size++; + } else { + /* rotate */ + ir_expression *tempptr = remainder_left; + ((ir_expression *)remainder)->operands[0] = tempptr->operands[1]; + tempptr->operands[1] = remainder; + remainder = tempptr; + ((ir_expression *)vine_tail)->operands[1] = tempptr; + } + } + + return size; +} + +static void +compression(ir_expression *root, unsigned count) +{ + ir_expression *scanner = root; + + for (unsigned i = 0; i < count; i++) { + ir_expression *child = (ir_expression *)scanner->operands[1]; + scanner->operands[1] = child->operands[1]; + scanner = (ir_expression *)scanner->operands[1]; + child->operands[1] = scanner->operands[0]; + scanner->operands[0] = child; + } +} + +static void +vine_to_tree(ir_expression *root, unsigned size) +{ + int n = size - 1; + for (int m = n / 2; m > 0; m = n / 2) { + compression(root, m); + n -= m + 1; + } +} + +namespace { + +class ir_rebalance_visitor : public ir_rvalue_enter_visitor { +public: + ir_rebalance_visitor() + { + progress = false; + } + + void handle_rvalue(ir_rvalue **rvalue); + + bool progress; +}; + +struct is_reduction_data { + ir_expression_operation operation; + const glsl_type *type; + unsigned num_expr; + bool is_reduction; + bool contains_constant; +}; + +} /* anonymous namespace */ + +static bool +is_reduction_operation(ir_expression_operation operation) +{ + switch (operation) { + case ir_binop_add: + case ir_binop_mul: + case ir_binop_bit_and: + case ir_binop_bit_xor: + case ir_binop_bit_or: + case ir_binop_logic_and: + case ir_binop_logic_xor: + case ir_binop_logic_or: + case ir_binop_min: + case ir_binop_max: + return true; + default: + return false; + } +} + +/* Note that this function does not attempt to recognize that reduction trees + * are already balanced. + * + * We return false from this function for a number of reasons other than an + * expression tree not being a mathematical reduction. Namely, + * + * - if the tree contains multiple constants that we may be able to combine. + * - if the tree contains matrices: + * - they might contain vec4's with many constant components that we can + * simplify after splitting. + * - applying the matrix chain ordering optimization is more than just + * balancing an expression tree. + * - if the tree contains operations on multiple types. + * - if the tree contains ir_dereference_{array,record}, since foo[a+b] + c + * would trick the visiting pass. + */ +static void +is_reduction(ir_instruction *ir, void *data) +{ + struct is_reduction_data *ird = (struct is_reduction_data *)data; + if (!ird->is_reduction) + return; + + /* We don't want to balance a tree that contains multiple constants, since + * we'll be able to constant fold them if they're not in separate subtrees. + */ + if (ir->as_constant()) { + if (ird->contains_constant) { + ird->is_reduction = false; + } + ird->contains_constant = true; + return; + } + + /* Array/record dereferences have subtrees that are not part of the expr + * tree we're balancing. Skip trees containing them. + */ + if (ir->ir_type == ir_type_dereference_array || + ir->ir_type == ir_type_dereference_record) { + ird->is_reduction = false; + return; + } + + ir_expression *expr = ir->as_expression(); + if (!expr) + return; + + /* Non-constant matrices might still contain constant vec4 that we can + * constant fold once split up. Handling matrices will need some more + * work. + */ + if (expr->type->is_matrix()) { + ird->is_reduction = false; + return; + } + + if (ird->type != NULL && ird->type != expr->type) { + ird->is_reduction = false; + return; + } + ird->type = expr->type; + + ird->num_expr++; + if (is_reduction_operation(expr->operation)) { + if (ird->operation != 0 && ird->operation != expr->operation) + ird->is_reduction = false; + ird->operation = expr->operation; + } else { + ird->is_reduction = false; + } +} + +static ir_rvalue * +handle_expression(ir_expression *expr) +{ + struct is_reduction_data ird; + ird.operation = (ir_expression_operation)0; + ird.type = NULL; + ird.num_expr = 0; + ird.is_reduction = true; + ird.contains_constant = false; + + visit_tree(expr, is_reduction, (void *)&ird); + + if (ird.is_reduction && ird.num_expr > 2) { + ir_constant z = ir_constant(0.0f); + ir_expression pseudo_root = ir_expression(ir_binop_add, &z, expr); + + unsigned size = tree_to_vine(&pseudo_root); + vine_to_tree(&pseudo_root, size); + + expr = (ir_expression *)pseudo_root.operands[1]; + } + return expr; +} + +void +ir_rebalance_visitor::handle_rvalue(ir_rvalue **rvalue) +{ + if (!*rvalue) + return; + + ir_expression *expr = (*rvalue)->as_expression(); + if (!expr || !is_reduction_operation(expr->operation)) + return; + + ir_rvalue *new_rvalue = handle_expression(expr); + + /* If we failed to rebalance the tree (e.g., because it wasn't a reduction, + * or some other set of cases) new_rvalue will point to the same root as + * before. + * + * Similarly, if the tree rooted at *rvalue was a reduction and was already + * balanced, the algorithm will rearrange the tree but will ultimately + * return an identical tree, so this check will handle that as well and + * will not set progress = true. + */ + if (new_rvalue == *rvalue) + return; + + *rvalue = new_rvalue; + this->progress = true; +} + +bool +do_rebalance_tree(exec_list *instructions) +{ + ir_rebalance_visitor v; + + v.run(instructions); + + return v.progress; +} diff --git a/mesalib/src/glsl/standalone_scaffolding.cpp b/mesalib/src/glsl/standalone_scaffolding.cpp index 6c25010b7..809732c7e 100644 --- a/mesalib/src/glsl/standalone_scaffolding.cpp +++ b/mesalib/src/glsl/standalone_scaffolding.cpp @@ -98,6 +98,7 @@ void initialize_context_to_defaults(struct gl_context *ctx, gl_api api) ctx->Extensions.ARB_ES3_compatibility = true; ctx->Extensions.ARB_explicit_attrib_location = true; ctx->Extensions.ARB_fragment_coord_conventions = true; + ctx->Extensions.ARB_fragment_layer_viewport = true; ctx->Extensions.ARB_gpu_shader5 = true; ctx->Extensions.ARB_sample_shading = true; ctx->Extensions.ARB_shader_bit_encoding = true; diff --git a/mesalib/src/glsl/test_optpass.cpp b/mesalib/src/glsl/test_optpass.cpp index db5cb2662..e4878bf15 100644 --- a/mesalib/src/glsl/test_optpass.cpp +++ b/mesalib/src/glsl/test_optpass.cpp @@ -65,7 +65,7 @@ do_optimization(struct exec_list *ir, const char *optimization, if (sscanf(optimization, "do_common_optimization ( %d ) ", &int_0) == 1) { return do_common_optimization(ir, int_0 != 0, false, options, true); } else if (strcmp(optimization, "do_algebraic") == 0) { - return do_algebraic(ir, true); + return do_algebraic(ir, true, options); } else if (strcmp(optimization, "do_constant_folding") == 0) { return do_constant_folding(ir); } else if (strcmp(optimization, "do_constant_variable") == 0) { diff --git a/mesalib/src/mapi/glapi/gen/ARB_compressed_texture_pixel_storage.xml b/mesalib/src/mapi/glapi/gen/ARB_compressed_texture_pixel_storage.xml new file mode 100644 index 000000000..c9d0f11be --- /dev/null +++ b/mesalib/src/mapi/glapi/gen/ARB_compressed_texture_pixel_storage.xml @@ -0,0 +1,21 @@ +<?xml version="1.0"?> +<!DOCTYPE OpenGLAPI SYSTEM "gl_API.dtd"> + +<OpenGLAPI> + +<category name="GL_ARB_compressed_texture_pixel_storage" number="110"> + + <enum name="UNPACK_COMPRESSED_BLOCK_WIDTH" value="0x9127"/> + <enum name="UNPACK_COMPRESSED_BLOCK_HEIGHT" value="0x9128"/> + <enum name="UNPACK_COMPRESSED_BLOCK_DEPTH" value="0x9129"/> + <enum name="UNPACK_COMPRESSED_BLOCK_SIZE" value="0x912A"/> + + <enum name="PACK_COMPRESSED_BLOCK_WIDTH" value="0x912B"/> + <enum name="PACK_COMPRESSED_BLOCK_HEIGHT" value="0x912C"/> + <enum name="PACK_COMPRESSED_BLOCK_DEPTH" value="0x912D"/> + <enum name="PACK_COMPRESSED_BLOCK_SIZE" value="0x912E"/> + +</category> + +</OpenGLAPI> + diff --git a/mesalib/src/mapi/glapi/gen/Makefile.am b/mesalib/src/mapi/glapi/gen/Makefile.am index 6f36989bc..be7d9e0ef 100644 --- a/mesalib/src/mapi/glapi/gen/Makefile.am +++ b/mesalib/src/mapi/glapi/gen/Makefile.am @@ -113,6 +113,7 @@ API_XML = \ ARB_blend_func_extended.xml \ ARB_clear_buffer_object.xml \ ARB_color_buffer_float.xml \ + ARB_compressed_texture_pixel_storage.xml \ ARB_compute_shader.xml \ ARB_copy_buffer.xml \ ARB_debug_output.xml \ diff --git a/mesalib/src/mapi/glapi/gen/gl_API.xml b/mesalib/src/mapi/glapi/gen/gl_API.xml index 58aed8e6f..a43410322 100755 --- a/mesalib/src/mapi/glapi/gen/gl_API.xml +++ b/mesalib/src/mapi/glapi/gen/gl_API.xml @@ -8276,7 +8276,9 @@ </function> </category> -<!-- ARB extensions #110...#116 --> +<xi:include href="ARB_compressed_texture_pixel_storage.xml" xmlns:xi="http://www.w3.org/2001/XInclude"/> + +<!-- ARB extensions #111...#116 --> <xi:include href="ARB_internalformat_query.xml" xmlns:xi="http://www.w3.org/2001/XInclude"/> @@ -8310,7 +8312,19 @@ <xi:include href="ARB_ES3_compatibility.xml" xmlns:xi="http://www.w3.org/2001/XInclude"/> -<!-- ARB extensions #128...#131 --> +<!-- ARB extension #128 --> + +<category name="GL_ARB_fragment_layer_viewport" number="129"> + <!-- No new functions, types, enums. --> +</category> + +<!-- ARB extensions #130..#131 --> + +<category name="GL_ARB_explicit_uniform_location" number="128"> + <enum name="MAX_UNIFORM_LOCATIONS" count="1" value="0x826E" > + <size name="Get" mode="get"/> + </enum> +</category> <xi:include href="ARB_invalidate_subdata.xml" xmlns:xi="http://www.w3.org/2001/XInclude"/> diff --git a/mesalib/src/mesa/Android.libmesa_dricore.mk b/mesalib/src/mesa/Android.libmesa_dricore.mk index 0db5825de..217f6498a 100644 --- a/mesalib/src/mesa/Android.libmesa_dricore.mk +++ b/mesalib/src/mesa/Android.libmesa_dricore.mk @@ -47,10 +47,16 @@ ifeq ($(TARGET_ARCH),x86) endif # x86 endif # MESA_ENABLE_ASM +ifeq ($(ARCH_X86_HAVE_SSE4_1),true) +LOCAL_SRC_FILES += \ + $(SRCDIR)main/streaming-load-memcpy.c +endif + LOCAL_C_INCLUDES := \ $(call intermediates-dir-for STATIC_LIBRARIES,libmesa_program,,) \ $(MESA_TOP)/src/mapi \ - $(MESA_TOP)/src/glsl + $(MESA_TOP)/src/glsl \ + $(MESA_TOP)/src/gallium/auxiliary LOCAL_WHOLE_STATIC_LIBRARIES := \ libmesa_program diff --git a/mesalib/src/mesa/Android.libmesa_glsl_utils.mk b/mesalib/src/mesa/Android.libmesa_glsl_utils.mk index 47f2e151b..e93891f07 100644 --- a/mesalib/src/mesa/Android.libmesa_glsl_utils.mk +++ b/mesalib/src/mesa/Android.libmesa_glsl_utils.mk @@ -56,6 +56,7 @@ include $(CLEAR_VARS) LOCAL_MODULE := libmesa_glsl_utils LOCAL_IS_HOST_MODULE := true +LOCAL_CFLAGS := -D_POSIX_C_SOURCE=199309L LOCAL_C_INCLUDES := \ $(MESA_TOP)/src/glsl \ diff --git a/mesalib/src/mesa/Android.mesa_gen_matypes.mk b/mesalib/src/mesa/Android.mesa_gen_matypes.mk index 6e301f904..5521087c4 100644 --- a/mesalib/src/mesa/Android.mesa_gen_matypes.mk +++ b/mesalib/src/mesa/Android.mesa_gen_matypes.mk @@ -33,6 +33,7 @@ include $(CLEAR_VARS) LOCAL_MODULE := mesa_gen_matypes LOCAL_IS_HOST_MODULE := true +LOCAL_CFLAGS := -D_POSIX_C_SOURCE=199309L LOCAL_C_INCLUDES := \ $(MESA_TOP)/src/mapi \ diff --git a/mesalib/src/mesa/drivers/common/meta.c b/mesalib/src/mesa/drivers/common/meta.c index fec0d2be5..1a2e45320 100644 --- a/mesalib/src/mesa/drivers/common/meta.c +++ b/mesalib/src/mesa/drivers/common/meta.c @@ -801,7 +801,7 @@ _mesa_meta_begin(struct gl_context *ctx, GLbitfield state) int buf, real_color_buffers = 0; memset(save->ColorDrawBuffers, 0, sizeof(save->ColorDrawBuffers)); - for (buf = 0; buf < MAX_DRAW_BUFFERS; buf++) { + for (buf = 0; buf < ctx->Const.MaxDrawBuffers; buf++) { int buf_index = ctx->DrawBuffer->_ColorDrawBufferIndexes[buf]; if (buf_index == -1) continue; @@ -1213,7 +1213,7 @@ _mesa_meta_end(struct gl_context *ctx) _mesa_BindRenderbuffer(GL_RENDERBUFFER, save->RenderbufferName); if (state & MESA_META_DRAW_BUFFERS) { - _mesa_DrawBuffers(MAX_DRAW_BUFFERS, save->ColorDrawBuffers); + _mesa_DrawBuffers(ctx->Const.MaxDrawBuffers, save->ColorDrawBuffers); } ctx->Meta->SaveStackDepth--; @@ -1569,6 +1569,7 @@ meta_glsl_clear_init(struct gl_context *ctx, struct clear_state *clear) _mesa_AttachShader(clear->ShaderProg, vs); _mesa_DeleteShader(vs); _mesa_BindAttribLocation(clear->ShaderProg, 0, "position"); + _mesa_ObjectLabel(GL_PROGRAM, clear->ShaderProg, -1, "meta clear"); _mesa_LinkProgram(clear->ShaderProg); clear->ColorLocation = _mesa_GetUniformLocation(clear->ShaderProg, @@ -2613,6 +2614,7 @@ _mesa_meta_setup_texture_coords(GLenum faceTarget, break; default: assert(0); + unreachable(); } coord[3] = (float) (slice / 6); diff --git a/mesalib/src/mesa/drivers/common/meta_blit.c b/mesalib/src/mesa/drivers/common/meta_blit.c index f26ef93c1..bbf0c3c45 100644 --- a/mesalib/src/mesa/drivers/common/meta_blit.c +++ b/mesalib/src/mesa/drivers/common/meta_blit.c @@ -407,7 +407,7 @@ blitframebuffer_texture(struct gl_context *ctx, } } else { GLenum tex_base_format; - int srcW = abs(srcY1 - srcY0); + int srcW = abs(srcX1 - srcX0); int srcH = abs(srcY1 - srcY0); /* Fall back to doing a CopyTexSubImage to get the destination * renderbuffer into a texture. diff --git a/mesalib/src/mesa/drivers/common/meta_generate_mipmap.c b/mesalib/src/mesa/drivers/common/meta_generate_mipmap.c index d12806c3d..4b1718df9 100644 --- a/mesalib/src/mesa/drivers/common/meta_generate_mipmap.c +++ b/mesalib/src/mesa/drivers/common/meta_generate_mipmap.c @@ -43,6 +43,7 @@ #include "main/varray.h" #include "main/viewport.h" #include "drivers/common/meta.h" +#include "program/prog_instruction.h" /** @@ -168,6 +169,8 @@ _mesa_meta_GenerateMipmap(struct gl_context *ctx, GLenum target, GLenum faceTarget; GLuint dstLevel; GLuint samplerSave; + GLint swizzle[4]; + GLboolean swizzleSaved = GL_FALSE; if (fallback_required(ctx, target, texObj)) { _mesa_generate_mipmap(ctx, target, texObj); @@ -231,6 +234,13 @@ _mesa_meta_GenerateMipmap(struct gl_context *ctx, GLenum target, _mesa_TexParameteri(target, GL_GENERATE_MIPMAP, GL_FALSE); + if (texObj->_Swizzle != SWIZZLE_NOOP) { + static const GLint swizzleNoop[4] = { GL_RED, GL_GREEN, GL_BLUE, GL_ALPHA }; + memcpy(swizzle, texObj->Swizzle, sizeof(swizzle)); + swizzleSaved = GL_TRUE; + _mesa_TexParameteriv(target, GL_TEXTURE_SWIZZLE_RGBA, swizzleNoop); + } + /* Silence valgrind warnings about reading uninitialized stack. */ memset(verts, 0, sizeof(verts)); @@ -347,4 +357,6 @@ _mesa_meta_GenerateMipmap(struct gl_context *ctx, GLenum target, _mesa_TexParameteri(target, GL_TEXTURE_MAX_LEVEL, maxLevelSave); if (genMipmapSave) _mesa_TexParameteri(target, GL_GENERATE_MIPMAP, genMipmapSave); + if (swizzleSaved) + _mesa_TexParameteriv(target, GL_TEXTURE_SWIZZLE_RGBA, swizzle); } diff --git a/mesalib/src/mesa/drivers/dri/Android.mk b/mesalib/src/mesa/drivers/dri/Android.mk index 9adf0b386..e0cf51c58 100644 --- a/mesalib/src/mesa/drivers/dri/Android.mk +++ b/mesalib/src/mesa/drivers/dri/Android.mk @@ -43,6 +43,7 @@ MESA_DRI_C_INCLUDES := \ MESA_DRI_WHOLE_STATIC_LIBRARIES := \ libmesa_glsl \ + libmegadriver_stub \ libmesa_dri_common \ libmesa_dricore diff --git a/mesalib/src/mesa/drivers/dri/common/Android.mk b/mesalib/src/mesa/drivers/dri/common/Android.mk index 0489a32de..a172a0bc6 100644 --- a/mesalib/src/mesa/drivers/dri/common/Android.mk +++ b/mesalib/src/mesa/drivers/dri/common/Android.mk @@ -86,3 +86,20 @@ $(intermediates)/xmlpool/options.h: $$(PRIVATE_SCRIPT) $$(PRIVATE_TEMPLATE_HEADE include $(MESA_COMMON_MK) include $(BUILD_STATIC_LIBRARY) + +# +# Build libmegadriver_stub +# + +include $(CLEAR_VARS) +include $(LOCAL_PATH)/Makefile.sources + +LOCAL_MODULE := libmegadriver_stub +LOCAL_MODULE_CLASS := STATIC_LIBRARIES +LOCAL_C_INCLUDES := \ + $(MESA_DRI_C_INCLUDES) + +LOCAL_SRC_FILES := $(megadriver_stub_FILES) + +include $(MESA_COMMON_MK) +include $(BUILD_STATIC_LIBRARY) diff --git a/mesalib/src/mesa/drivers/dri/common/Makefile.am b/mesalib/src/mesa/drivers/dri/common/Makefile.am index c98ccf7b8..7222a96c6 100644 --- a/mesalib/src/mesa/drivers/dri/common/Makefile.am +++ b/mesalib/src/mesa/drivers/dri/common/Makefile.am @@ -42,7 +42,7 @@ libdricommon_la_SOURCES = $(DRI_COMMON_FILES) libdri_test_stubs_la_SOURCES = $(test_stubs_FILES) libdri_test_stubs_la_CFLAGS = $(AM_CFLAGS) -DNO_MAIN -libmegadriver_stub_la_SOURCES = megadriver_stub.c +libmegadriver_stub_la_SOURCES = $(megadriver_stub_FILES) sysconf_DATA = drirc diff --git a/mesalib/src/mesa/drivers/dri/common/Makefile.sources b/mesalib/src/mesa/drivers/dri/common/Makefile.sources index 8469b4950..43b289e90 100644 --- a/mesalib/src/mesa/drivers/dri/common/Makefile.sources +++ b/mesalib/src/mesa/drivers/dri/common/Makefile.sources @@ -14,3 +14,6 @@ mesa_dri_common_INCLUDES := \ test_stubs_FILES := \ dri_test.c + +megadriver_stub_FILES := \ + megadriver_stub.c diff --git a/mesalib/src/mesa/main/api_arrayelt.c b/mesalib/src/mesa/main/api_arrayelt.c index 05cbc0f1f..ebeba8883 100644 --- a/mesalib/src/mesa/main/api_arrayelt.c +++ b/mesalib/src/mesa/main/api_arrayelt.c @@ -43,18 +43,21 @@ #include "macros.h" #include "mtypes.h" #include "main/dispatch.h" +#include "varray.h" typedef void (GLAPIENTRY *array_func)( const void * ); typedef struct { - const struct gl_client_array *array; + const struct gl_vertex_attrib_array *array; + const struct gl_vertex_buffer_binding *binding; int offset; } AEarray; typedef void (GLAPIENTRY *attrib_func)( GLuint indx, const void *data ); typedef struct { - const struct gl_client_array *array; + const struct gl_vertex_attrib_array *array; + const struct gl_vertex_buffer_binding *binding; attrib_func func; GLuint index; } AEattrib; @@ -1470,18 +1473,6 @@ check_vbo(AEcontext *actx, struct gl_buffer_object *vbo) } -static inline void -update_derived_client_arrays(struct gl_context *ctx) -{ - struct gl_vertex_array_object *vao = ctx->Array.VAO; - - if (vao->NewArrays) { - _mesa_update_vao_client_arrays(ctx, vao); - vao->NewArrays = 0; - } -} - - /** * Make a list of per-vertex functions to call for each glArrayElement call. * These functions access the array data (i.e. glVertex, glColor, glNormal, @@ -1500,67 +1491,81 @@ _ae_update_state(struct gl_context *ctx) actx->nr_vbos = 0; /* conventional vertex arrays */ - if (vao->_VertexAttrib[VERT_ATTRIB_COLOR_INDEX].Enabled) { - aa->array = &vao->_VertexAttrib[VERT_ATTRIB_COLOR_INDEX]; + if (vao->VertexAttrib[VERT_ATTRIB_COLOR_INDEX].Enabled) { + aa->array = &vao->VertexAttrib[VERT_ATTRIB_COLOR_INDEX]; + aa->binding = &vao->VertexBinding[aa->array->VertexBinding]; aa->offset = IndexFuncs[TYPE_IDX(aa->array->Type)]; - check_vbo(actx, aa->array->BufferObj); + check_vbo(actx, aa->binding->BufferObj); aa++; } - if (vao->_VertexAttrib[VERT_ATTRIB_EDGEFLAG].Enabled) { - aa->array = &vao->_VertexAttrib[VERT_ATTRIB_EDGEFLAG]; + + if (vao->VertexAttrib[VERT_ATTRIB_EDGEFLAG].Enabled) { + aa->array = &vao->VertexAttrib[VERT_ATTRIB_EDGEFLAG]; + aa->binding = &vao->VertexBinding[aa->array->VertexBinding]; aa->offset = _gloffset_EdgeFlagv; - check_vbo(actx, aa->array->BufferObj); + check_vbo(actx, aa->binding->BufferObj); aa++; } - if (vao->_VertexAttrib[VERT_ATTRIB_NORMAL].Enabled) { - aa->array = &vao->_VertexAttrib[VERT_ATTRIB_NORMAL]; + + if (vao->VertexAttrib[VERT_ATTRIB_NORMAL].Enabled) { + aa->array = &vao->VertexAttrib[VERT_ATTRIB_NORMAL]; + aa->binding = &vao->VertexBinding[aa->array->VertexBinding]; aa->offset = NormalFuncs[TYPE_IDX(aa->array->Type)]; - check_vbo(actx, aa->array->BufferObj); + check_vbo(actx, aa->binding->BufferObj); aa++; } - if (vao->_VertexAttrib[VERT_ATTRIB_COLOR0].Enabled) { - aa->array = &vao->_VertexAttrib[VERT_ATTRIB_COLOR0]; + + if (vao->VertexAttrib[VERT_ATTRIB_COLOR0].Enabled) { + aa->array = &vao->VertexAttrib[VERT_ATTRIB_COLOR0]; + aa->binding = &vao->VertexBinding[aa->array->VertexBinding]; aa->offset = ColorFuncs[aa->array->Size-3][TYPE_IDX(aa->array->Type)]; - check_vbo(actx, aa->array->BufferObj); + check_vbo(actx, aa->binding->BufferObj); aa++; } - if (vao->_VertexAttrib[VERT_ATTRIB_COLOR1].Enabled) { - aa->array = &vao->_VertexAttrib[VERT_ATTRIB_COLOR1]; + + if (vao->VertexAttrib[VERT_ATTRIB_COLOR1].Enabled) { + aa->array = &vao->VertexAttrib[VERT_ATTRIB_COLOR1]; + aa->binding = &vao->VertexBinding[aa->array->VertexBinding]; aa->offset = SecondaryColorFuncs[TYPE_IDX(aa->array->Type)]; - check_vbo(actx, aa->array->BufferObj); + check_vbo(actx, aa->binding->BufferObj); aa++; } - if (vao->_VertexAttrib[VERT_ATTRIB_FOG].Enabled) { - aa->array = &vao->_VertexAttrib[VERT_ATTRIB_FOG]; + + if (vao->VertexAttrib[VERT_ATTRIB_FOG].Enabled) { + aa->array = &vao->VertexAttrib[VERT_ATTRIB_FOG]; + aa->binding = &vao->VertexBinding[aa->array->VertexBinding]; aa->offset = FogCoordFuncs[TYPE_IDX(aa->array->Type)]; - check_vbo(actx, aa->array->BufferObj); + check_vbo(actx, aa->binding->BufferObj); aa++; } + for (i = 0; i < ctx->Const.MaxTextureCoordUnits; i++) { - struct gl_client_array *attribArray = - &vao->_VertexAttrib[VERT_ATTRIB_TEX(i)]; + struct gl_vertex_attrib_array *attribArray = + &vao->VertexAttrib[VERT_ATTRIB_TEX(i)]; if (attribArray->Enabled) { /* NOTE: we use generic glVertexAttribNV functions here. * If we ever remove GL_NV_vertex_program this will have to change. */ at->array = attribArray; + at->binding = &vao->VertexBinding[attribArray->VertexBinding]; ASSERT(!at->array->Normalized); at->func = AttribFuncsNV[at->array->Normalized] [at->array->Size-1] [TYPE_IDX(at->array->Type)]; at->index = VERT_ATTRIB_TEX0 + i; - check_vbo(actx, at->array->BufferObj); + check_vbo(actx, at->binding->BufferObj); at++; } } /* generic vertex attribute arrays */ for (i = 1; i < VERT_ATTRIB_GENERIC_MAX; i++) { /* skip zero! */ - struct gl_client_array *attribArray = - &vao->_VertexAttrib[VERT_ATTRIB_GENERIC(i)]; + struct gl_vertex_attrib_array *attribArray = + &vao->VertexAttrib[VERT_ATTRIB_GENERIC(i)]; if (attribArray->Enabled) { GLint intOrNorm; at->array = attribArray; + at->binding = &vao->VertexBinding[attribArray->VertexBinding]; /* Note: we can't grab the _glapi_Dispatch->VertexAttrib1fvNV * function pointer here (for float arrays) since the pointer may * change from one execution of _ae_ArrayElement() to @@ -1578,26 +1583,28 @@ _ae_update_state(struct gl_context *ctx) [TYPE_IDX(at->array->Type)]; at->index = i; - check_vbo(actx, at->array->BufferObj); + check_vbo(actx, at->binding->BufferObj); at++; } } /* finally, vertex position */ - if (vao->_VertexAttrib[VERT_ATTRIB_GENERIC0].Enabled) { + if (vao->VertexAttrib[VERT_ATTRIB_GENERIC0].Enabled) { /* Use glVertex(v) instead of glVertexAttrib(0, v) to be sure it's * issued as the last (provoking) attribute). */ - aa->array = &vao->_VertexAttrib[VERT_ATTRIB_GENERIC0]; + aa->array = &vao->VertexAttrib[VERT_ATTRIB_GENERIC0]; + aa->binding = &vao->VertexBinding[aa->array->VertexBinding]; assert(aa->array->Size >= 2); /* XXX fix someday? */ aa->offset = VertexFuncs[aa->array->Size-2][TYPE_IDX(aa->array->Type)]; - check_vbo(actx, aa->array->BufferObj); + check_vbo(actx, aa->binding->BufferObj); aa++; } - else if (vao->_VertexAttrib[VERT_ATTRIB_POS].Enabled) { - aa->array = &vao->_VertexAttrib[VERT_ATTRIB_POS]; + else if (vao->VertexAttrib[VERT_ATTRIB_POS].Enabled) { + aa->array = &vao->VertexAttrib[VERT_ATTRIB_POS]; + aa->binding = &vao->VertexBinding[aa->array->VertexBinding]; aa->offset = VertexFuncs[aa->array->Size-2][TYPE_IDX(aa->array->Type)]; - check_vbo(actx, aa->array->BufferObj); + check_vbo(actx, aa->binding->BufferObj); aa++; } @@ -1625,8 +1632,6 @@ _ae_map_vbos(struct gl_context *ctx) if (actx->mapped_vbos) return; - update_derived_client_arrays(ctx); - if (actx->NewState) _ae_update_state(ctx); @@ -1679,8 +1684,6 @@ _ae_ArrayElement(GLint elt) const struct _glapi_table * const disp = GET_DISPATCH(); GLboolean do_map; - update_derived_client_arrays(ctx); - /* If PrimitiveRestart is enabled and the index is the RestartIndex * then we call PrimitiveRestartNV and return. */ @@ -1703,18 +1706,18 @@ _ae_ArrayElement(GLint elt) /* emit generic attribute elements */ for (at = actx->attribs; at->func; at++) { const GLubyte *src - = ADD_POINTERS(at->array->BufferObj->Mappings[MAP_INTERNAL].Pointer, - at->array->Ptr) - + elt * at->array->StrideB; + = ADD_POINTERS(at->binding->BufferObj->Mappings[MAP_INTERNAL].Pointer, + _mesa_vertex_attrib_address(at->array, at->binding)) + + elt * at->binding->Stride; at->func(at->index, src); } /* emit conventional arrays elements */ for (aa = actx->arrays; aa->offset != -1 ; aa++) { const GLubyte *src - = ADD_POINTERS(aa->array->BufferObj->Mappings[MAP_INTERNAL].Pointer, - aa->array->Ptr) - + elt * aa->array->StrideB; + = ADD_POINTERS(aa->binding->BufferObj->Mappings[MAP_INTERNAL].Pointer, + _mesa_vertex_attrib_address(aa->array, aa->binding)) + + elt * aa->binding->Stride; CALL_by_offset(disp, (array_func), aa->offset, ((const void *) src)); } diff --git a/mesalib/src/mesa/main/clear.c b/mesalib/src/mesa/main/clear.c index 9df1f5e09..cf93418d1 100644 --- a/mesalib/src/mesa/main/clear.c +++ b/mesalib/src/mesa/main/clear.c @@ -180,11 +180,6 @@ _mesa_Clear( GLbitfield mask ) return; } - if (ctx->DrawBuffer->Width == 0 || ctx->DrawBuffer->Height == 0 || - ctx->DrawBuffer->_Xmin >= ctx->DrawBuffer->_Xmax || - ctx->DrawBuffer->_Ymin >= ctx->DrawBuffer->_Ymax) - return; - if (ctx->RasterDiscard) return; diff --git a/mesalib/src/mesa/main/context.c b/mesalib/src/mesa/main/context.c index 8eb426d59..244e63ede 100644 --- a/mesalib/src/mesa/main/context.c +++ b/mesalib/src/mesa/main/context.c @@ -396,6 +396,8 @@ one_time_init( struct gl_context *ctx ) assert( sizeof(GLint) == 4 ); assert( sizeof(GLuint) == 4 ); + _mesa_one_time_init_extension_overrides(); + _mesa_get_cpu_features(); for (i = 0; i < 256; i++) { @@ -610,6 +612,10 @@ _mesa_init_constants(struct gl_context *ctx) ctx->Const.MaxUniformBlockSize = 16384; ctx->Const.UniformBufferOffsetAlignment = 1; + /* GL_ARB_explicit_uniform_location, GL_MAX_UNIFORM_LOCATIONS */ + ctx->Const.MaxUserAssignableUniformLocations = + 4 * MESA_SHADER_STAGES * MAX_UNIFORMS; + for (i = 0; i < MESA_SHADER_STAGES; i++) init_program_limits(ctx, i, &ctx->Const.Program[i]); diff --git a/mesalib/src/mesa/main/extensions.c b/mesalib/src/mesa/main/extensions.c index c2ff7e3b7..25e3dab4f 100644 --- a/mesalib/src/mesa/main/extensions.c +++ b/mesalib/src/mesa/main/extensions.c @@ -37,6 +37,11 @@ #include "macros.h" #include "mtypes.h" +struct gl_extensions _mesa_extension_override_enables; +struct gl_extensions _mesa_extension_override_disables; +static char *extra_extensions = NULL; +static char *cant_disable_extensions = NULL; + enum { DISABLE = 0, GLL = 1 << API_OPENGL_COMPAT, /* GL Legacy / Compatibility */ @@ -86,6 +91,7 @@ static const struct extension extension_table[] = { { "GL_ARB_buffer_storage", o(ARB_buffer_storage), GL, 2013 }, { "GL_ARB_clear_buffer_object", o(dummy_true), GL, 2012 }, { "GL_ARB_color_buffer_float", o(ARB_color_buffer_float), GL, 2004 }, + { "GL_ARB_compressed_texture_pixel_storage", o(dummy_true), GL, 2011 }, { "GL_ARB_compute_shader", o(ARB_compute_shader), GL, 2012 }, { "GL_ARB_copy_buffer", o(dummy_true), GL, 2008 }, { "GL_ARB_conservative_depth", o(ARB_conservative_depth), GL, 2011 }, @@ -99,7 +105,9 @@ static const struct extension extension_table[] = { { "GL_ARB_draw_indirect", o(ARB_draw_indirect), GLC, 2010 }, { "GL_ARB_draw_instanced", o(ARB_draw_instanced), GL, 2008 }, { "GL_ARB_explicit_attrib_location", o(ARB_explicit_attrib_location), GL, 2009 }, + { "GL_ARB_explicit_uniform_location", o(ARB_explicit_uniform_location), GL, 2012 }, { "GL_ARB_fragment_coord_conventions", o(ARB_fragment_coord_conventions), GL, 2009 }, + { "GL_ARB_fragment_layer_viewport", o(ARB_fragment_layer_viewport), GLC, 2012 }, { "GL_ARB_fragment_program", o(ARB_fragment_program), GLL, 2002 }, { "GL_ARB_fragment_program_shadow", o(ARB_fragment_program_shadow), GLL, 2003 }, { "GL_ARB_fragment_shader", o(ARB_fragment_shader), GL, 2002 }, @@ -388,6 +396,31 @@ name_to_offset(const char* name) return 0; } +/** + * Overrides extensions in \c ctx based on the values in + * _mesa_extension_override_enables and _mesa_extension_override_disables. + */ +static void +override_extensions_in_context(struct gl_context *ctx) +{ + const struct extension *i; + const GLboolean *enables = + (GLboolean*) &_mesa_extension_override_enables; + const GLboolean *disables = + (GLboolean*) &_mesa_extension_override_disables; + GLboolean *ctx_ext = (GLboolean*)&ctx->Extensions; + + for (i = extension_table; i->name != 0; ++i) { + size_t offset = i->offset; + assert(!enables[offset] || !disables[offset]); + if (enables[offset]) { + ctx_ext[offset] = 1; + } else if (disables[offset]) { + ctx_ext[offset] = 0; + } + } +} + /** * Enable all extensions suitable for a software-only renderer. @@ -473,34 +506,19 @@ _mesa_enable_sw_extensions(struct gl_context *ctx) /** * Either enable or disable the named extension. - * \return GL_TRUE for success, GL_FALSE if invalid extension name + * \return offset of extensions withint `ext' or 0 if extension is not known */ -static GLboolean -set_extension( struct gl_context *ctx, const char *name, GLboolean state ) +static size_t +set_extension(struct gl_extensions *ext, const char *name, GLboolean state) { size_t offset; - if (ctx->Extensions.String) { - /* The string was already queried - can't change it now! */ - _mesa_problem(ctx, "Trying to enable/disable extension after " - "glGetString(GL_EXTENSIONS): %s", name); - return GL_FALSE; - } - offset = name_to_offset(name); - if (offset == 0) { - _mesa_problem(ctx, "Trying to enable/disable unknown extension %s", - name); - return GL_FALSE; - } else if (offset == o(dummy_true) && state == GL_FALSE) { - _mesa_problem(ctx, "Trying to disable a permanently enabled extension: " - "%s", name); - return GL_FALSE; - } else { - GLboolean *base = (GLboolean *) &ctx->Extensions; - base[offset] = state; - return GL_TRUE; + if (offset != 0 && (offset != o(dummy_true) || state != GL_FALSE)) { + ((GLboolean *) ext)[offset] = state; } + + return offset; } /** @@ -513,32 +531,80 @@ set_extension( struct gl_context *ctx, const char *name, GLboolean state ) * - Enable recognized extension names that are not prefixed. * - Collect unrecognized extension names in a new string. * + * \c MESA_EXTENSION_OVERRIDE was previously parsed during + * _mesa_one_time_init_extension_overrides. We just use the results of that + * parsing in this function. + * * \return Space-separated list of unrecognized extension names (which must * be freed). Does not return \c NULL. */ static char * get_extension_override( struct gl_context *ctx ) { + override_extensions_in_context(ctx); + + if (cant_disable_extensions != NULL) { + _mesa_problem(ctx, + "Trying to disable permanently enabled extensions: %s", + cant_disable_extensions); + } + + if (extra_extensions == NULL) { + return calloc(1, sizeof(char)); + } else { + _mesa_problem(ctx, "Trying to enable unknown extensions: %s", + extra_extensions); + return strdup(extra_extensions); + } +} + + +/** + * \brief Free extra_extensions and cant_disable_extensions strings + * + * These strings are allocated early during the first context creation by + * _mesa_one_time_init_extension_overrides. + */ +static void +free_unknown_extensions_strings(void) +{ + free(extra_extensions); + free(cant_disable_extensions); +} + + +/** + * \brief Initialize extension override tables. + * + * This should be called one time early during first context initialization. + */ +void +_mesa_one_time_init_extension_overrides(void) +{ const char *env_const = _mesa_getenv("MESA_EXTENSION_OVERRIDE"); char *env; char *ext; - char *extra_exts; int len; + size_t offset; + + atexit(free_unknown_extensions_strings); + + memset(&_mesa_extension_override_enables, 0, sizeof(struct gl_extensions)); + memset(&_mesa_extension_override_disables, 0, sizeof(struct gl_extensions)); if (env_const == NULL) { - /* Return the empty string rather than NULL. This simplifies the logic - * of client functions. */ - return calloc(4, sizeof(char)); + return; } /* extra_exts: List of unrecognized extensions. */ - extra_exts = calloc(ALIGN(strlen(env_const) + 2, 4), sizeof(char)); + extra_extensions = calloc(ALIGN(strlen(env_const) + 2, 4), sizeof(char)); + cant_disable_extensions = calloc(ALIGN(strlen(env_const) + 2, 4), sizeof(char)); /* Copy env_const because strtok() is destructive. */ env = strdup(env_const); for (ext = strtok(env, " "); ext != NULL; ext = strtok(NULL, " ")) { int enable; - int recognized; + bool recognized; switch (ext[0]) { case '+': enable = 1; @@ -552,21 +618,43 @@ get_extension_override( struct gl_context *ctx ) enable = 1; break; } - recognized = set_extension(ctx, ext, enable); + + offset = set_extension(&_mesa_extension_override_enables, ext, enable); + if (offset != 0 && (offset != o(dummy_true) || enable != GL_FALSE)) { + ((GLboolean *) &_mesa_extension_override_disables)[offset] = !enable; + recognized = true; + } else { + recognized = false; + } + if (!recognized) { - strcat(extra_exts, ext); - strcat(extra_exts, " "); + if (enable) { + strcat(extra_extensions, ext); + strcat(extra_extensions, " "); + } else if (offset == o(dummy_true)) { + strcat(cant_disable_extensions, ext); + strcat(cant_disable_extensions, " "); + } } } free(env); - /* Remove trailing space. */ - len = strlen(extra_exts); - if (len > 0 && extra_exts[len - 1] == ' ') - extra_exts[len - 1] = '\0'; - - return extra_exts; + /* Remove trailing space, and free if unused. */ + len = strlen(extra_extensions); + if (len == 0) { + free(extra_extensions); + extra_extensions = NULL; + } else if (extra_extensions[len - 1] == ' ') { + extra_extensions[len - 1] = '\0'; + } + len = strlen(cant_disable_extensions); + if (len == 0) { + free(cant_disable_extensions); + cant_disable_extensions = NULL; + } else if (cant_disable_extensions[len - 1] == ' ') { + cant_disable_extensions[len - 1] = '\0'; + } } diff --git a/mesalib/src/mesa/main/extensions.h b/mesalib/src/mesa/main/extensions.h index a8cc2a41e..3a404d2e0 100644 --- a/mesalib/src/mesa/main/extensions.h +++ b/mesalib/src/mesa/main/extensions.h @@ -39,9 +39,12 @@ #include "glheader.h" struct gl_context; +struct gl_extensions; extern void _mesa_enable_sw_extensions(struct gl_context *ctx); +extern void _mesa_one_time_init_extension_overrides(void); + extern void _mesa_init_extensions(struct gl_context *ctx); extern GLubyte *_mesa_make_extension_string(struct gl_context *ctx); @@ -52,4 +55,7 @@ _mesa_get_extension_count(struct gl_context *ctx); extern const GLubyte * _mesa_get_enabled_extension(struct gl_context *ctx, GLuint index); +extern struct gl_extensions _mesa_extension_override_enables; +extern struct gl_extensions _mesa_extension_override_disables; + #endif diff --git a/mesalib/src/mesa/main/ff_fragment_shader.cpp b/mesalib/src/mesa/main/ff_fragment_shader.cpp index 8c360970f..211583738 100644 --- a/mesalib/src/mesa/main/ff_fragment_shader.cpp +++ b/mesalib/src/mesa/main/ff_fragment_shader.cpp @@ -877,14 +877,15 @@ emit_texenv(texenv_fragment_program *p, GLuint unit) shift = new(p->mem_ctx) ir_constant((float)(1 << rgb_shift)); } else { - float const_data[4] = { - float(1 << rgb_shift), - float(1 << rgb_shift), - float(1 << rgb_shift), - float(1 << alpha_shift) - }; - shift = new(p->mem_ctx) ir_constant(glsl_type::vec4_type, - (ir_constant_data *)const_data); + ir_constant_data const_data; + + const_data.f[0] = float(1 << rgb_shift); + const_data.f[1] = float(1 << rgb_shift); + const_data.f[2] = float(1 << rgb_shift); + const_data.f[3] = float(1 << alpha_shift); + + shift = new(p->mem_ctx) ir_constant(glsl_type::vec4_type, + &const_data); } return saturate(mul(deref, shift)); diff --git a/mesalib/src/mesa/main/get.c b/mesalib/src/mesa/main/get.c index 9b56edb74..0e2d8f687 100644 --- a/mesalib/src/mesa/main/get.c +++ b/mesalib/src/mesa/main/get.c @@ -278,11 +278,6 @@ static const int extra_flush_current[] = { EXTRA_END }; -static const int extra_EXT_texture_integer[] = { - EXT(EXT_texture_integer), - EXTRA_END -}; - static const int extra_EXT_texture_integer_and_new_buffers[] = { EXT(EXT_texture_integer), EXTRA_NEW_BUFFERS, @@ -395,6 +390,7 @@ EXTRA_EXT(ARB_compute_shader); EXTRA_EXT(ARB_gpu_shader5); EXTRA_EXT2(ARB_transform_feedback3, ARB_gpu_shader5); EXTRA_EXT(INTEL_performance_query); +EXTRA_EXT(ARB_explicit_uniform_location); static const int extra_ARB_color_buffer_float_or_glcore[] = { diff --git a/mesalib/src/mesa/main/get_hash_params.py b/mesalib/src/mesa/main/get_hash_params.py index c7a6e02af..d45962d95 100644 --- a/mesalib/src/mesa/main/get_hash_params.py +++ b/mesalib/src/mesa/main/get_hash_params.py @@ -480,6 +480,7 @@ descriptor=[ [ "MAX_LIST_NESTING", "CONST(MAX_LIST_NESTING), NO_EXTRA" ], [ "MAX_NAME_STACK_DEPTH", "CONST(MAX_NAME_STACK_DEPTH), NO_EXTRA" ], [ "MAX_PIXEL_MAP_TABLE", "CONST(MAX_PIXEL_MAP_TABLE), NO_EXTRA" ], + [ "MAX_UNIFORM_LOCATIONS", "CONTEXT_INT(Const.MaxUserAssignableUniformLocations), extra_ARB_explicit_uniform_location" ], [ "NAME_STACK_DEPTH", "CONTEXT_INT(Select.NameStackDepth), NO_EXTRA" ], [ "PACK_LSB_FIRST", "CONTEXT_BOOL(Pack.LsbFirst), NO_EXTRA" ], [ "PACK_SWAP_BYTES", "CONTEXT_BOOL(Pack.SwapBytes), NO_EXTRA" ], @@ -541,6 +542,16 @@ descriptor=[ [ "ARRAY_ELEMENT_LOCK_FIRST_EXT", "CONTEXT_INT(Array.LockFirst), NO_EXTRA" ], [ "ARRAY_ELEMENT_LOCK_COUNT_EXT", "CONTEXT_INT(Array.LockCount), NO_EXTRA" ], +# GL_ARB_compressed_texture_pixel_storage + [ "UNPACK_COMPRESSED_BLOCK_WIDTH", "CONTEXT_INT(Unpack.CompressedBlockWidth), NO_EXTRA" ], + [ "UNPACK_COMPRESSED_BLOCK_HEIGHT", "CONTEXT_INT(Unpack.CompressedBlockHeight), NO_EXTRA" ], + [ "UNPACK_COMPRESSED_BLOCK_DEPTH", "CONTEXT_INT(Unpack.CompressedBlockDepth), NO_EXTRA" ], + [ "UNPACK_COMPRESSED_BLOCK_SIZE", "CONTEXT_INT(Unpack.CompressedBlockSize), NO_EXTRA" ], + [ "PACK_COMPRESSED_BLOCK_WIDTH", "CONTEXT_INT(Pack.CompressedBlockWidth), NO_EXTRA" ], + [ "PACK_COMPRESSED_BLOCK_HEIGHT", "CONTEXT_INT(Pack.CompressedBlockHeight), NO_EXTRA" ], + [ "PACK_COMPRESSED_BLOCK_DEPTH", "CONTEXT_INT(Pack.CompressedBlockDepth), NO_EXTRA" ], + [ "PACK_COMPRESSED_BLOCK_SIZE", "CONTEXT_INT(Pack.CompressedBlockSize), NO_EXTRA" ], + # GL_ARB_transpose_matrix [ "TRANSPOSE_MODELVIEW_MATRIX_ARB", "CONTEXT_MATRIX_T(ModelviewMatrixStack), NO_EXTRA" ], [ "TRANSPOSE_PROJECTION_MATRIX_ARB", "CONTEXT_MATRIX_T(ProjectionMatrixStack.Top), NO_EXTRA" ], diff --git a/mesalib/src/mesa/main/glformats.c b/mesalib/src/mesa/main/glformats.c index 9bb341cc0..aee336e12 100644 --- a/mesalib/src/mesa/main/glformats.c +++ b/mesalib/src/mesa/main/glformats.c @@ -458,36 +458,6 @@ _mesa_is_enum_format_integer(GLenum format) } -/** - * Test if the given type is an integer (non-normalized) format. - */ -GLboolean -_mesa_is_type_integer(GLenum type) -{ - switch (type) { - case GL_INT: - case GL_UNSIGNED_INT: - case GL_SHORT: - case GL_UNSIGNED_SHORT: - case GL_BYTE: - case GL_UNSIGNED_BYTE: - return GL_TRUE; - default: - return GL_FALSE; - } -} - - -/** - * Test if the given format or type is an integer (non-normalized) format. - */ -extern GLboolean -_mesa_is_enum_format_or_type_integer(GLenum format, GLenum type) -{ - return _mesa_is_enum_format_integer(format) || _mesa_is_type_integer(type); -} - - GLboolean _mesa_is_type_unsigned(GLenum type) { diff --git a/mesalib/src/mesa/main/glformats.h b/mesalib/src/mesa/main/glformats.h index af1089931..ccbce2dab 100644 --- a/mesalib/src/mesa/main/glformats.h +++ b/mesalib/src/mesa/main/glformats.h @@ -54,9 +54,6 @@ extern GLint _mesa_bytes_per_vertex_attrib(GLint comps, GLenum type); extern GLboolean -_mesa_is_type_integer(GLenum type); - -extern GLboolean _mesa_is_type_unsigned(GLenum type); extern GLboolean @@ -69,9 +66,6 @@ extern GLboolean _mesa_is_enum_format_signed_int(GLenum format); extern GLboolean -_mesa_is_enum_format_or_type_integer(GLenum format, GLenum type); - -extern GLboolean _mesa_is_color_format(GLenum format); extern GLboolean diff --git a/mesalib/src/mesa/main/mtypes.h b/mesalib/src/mesa/main/mtypes.h index 917d071a2..4762d9616 100644 --- a/mesalib/src/mesa/main/mtypes.h +++ b/mesalib/src/mesa/main/mtypes.h @@ -1502,6 +1502,10 @@ struct gl_pixelstore_attrib GLboolean SwapBytes; GLboolean LsbFirst; GLboolean Invert; /**< GL_MESA_pack_invert */ + GLint CompressedBlockWidth; /**< GL_ARB_compressed_texture_pixel_storage */ + GLint CompressedBlockHeight; + GLint CompressedBlockDepth; + GLint CompressedBlockSize; struct gl_buffer_object *BufferObj; /**< GL_ARB_pixel_buffer_object */ }; @@ -2172,7 +2176,7 @@ struct gl_geometry_program GLenum InputType; /**< GL_POINTS, GL_LINES, GL_LINES_ADJACENCY_ARB, GL_TRIANGLES, or GL_TRIANGLES_ADJACENCY_ARB */ GLenum OutputType; /**< GL_POINTS, GL_LINE_STRIP or GL_TRIANGLE_STRIP */ - GLboolean UsesEndPrimitive; + bool UsesEndPrimitive; }; @@ -2675,7 +2679,7 @@ struct gl_shader_program GLboolean UsesClipDistance; GLuint ClipDistanceArraySize; /**< Size of the gl_ClipDistance array, or 0 if not present. */ - GLboolean UsesEndPrimitive; + bool UsesEndPrimitive; } Geom; /** Vertex shader state */ @@ -3319,6 +3323,11 @@ struct gl_constants GLuint UniformBufferOffsetAlignment; /** @} */ + /** + * GL_ARB_explicit_uniform_location + */ + GLuint MaxUserAssignableUniformLocations; + /** GL_ARB_geometry_shader4 */ GLuint MaxGeometryOutputVertices; GLuint MaxGeometryTotalOutputComponents; @@ -3511,11 +3520,13 @@ struct gl_extensions GLboolean ARB_draw_indirect; GLboolean ARB_draw_instanced; GLboolean ARB_fragment_coord_conventions; + GLboolean ARB_fragment_layer_viewport; GLboolean ARB_fragment_program; GLboolean ARB_fragment_program_shadow; GLboolean ARB_fragment_shader; GLboolean ARB_framebuffer_object; GLboolean ARB_explicit_attrib_location; + GLboolean ARB_explicit_uniform_location; GLboolean ARB_geometry_shader4; GLboolean ARB_gpu_shader5; GLboolean ARB_half_float_vertex; diff --git a/mesalib/src/mesa/main/performance_monitor.c b/mesalib/src/mesa/main/performance_monitor.c index 9d1a6b4d8..c26eda4c6 100644 --- a/mesalib/src/mesa/main/performance_monitor.c +++ b/mesalib/src/mesa/main/performance_monitor.c @@ -164,19 +164,6 @@ counterid_to_index(GLuint counterid) return counterid - 1; } -static inline GLuint -index_to_counterid(GLuint index) -{ - return index + 1; -} - -static inline bool -counterid_valid(const struct gl_perf_monitor_group *group_obj, - GLuint counterid) -{ - return get_counter(group_obj, counterid_to_index(counterid)) != NULL; -} - /*****************************************************************************/ void GLAPIENTRY diff --git a/mesalib/src/mesa/main/pixelstore.c b/mesalib/src/mesa/main/pixelstore.c index 0f55bc304..05f6583a4 100644 --- a/mesalib/src/mesa/main/pixelstore.c +++ b/mesalib/src/mesa/main/pixelstore.c @@ -45,176 +45,165 @@ _mesa_PixelStorei( GLenum pname, GLint param ) case GL_PACK_SWAP_BYTES: if (!_mesa_is_desktop_gl(ctx)) goto invalid_enum_error; - if (param == (GLint)ctx->Pack.SwapBytes) - return; ctx->Pack.SwapBytes = param ? GL_TRUE : GL_FALSE; - break; + break; case GL_PACK_LSB_FIRST: if (!_mesa_is_desktop_gl(ctx)) goto invalid_enum_error; - if (param == (GLint)ctx->Pack.LsbFirst) - return; ctx->Pack.LsbFirst = param ? GL_TRUE : GL_FALSE; - break; + break; case GL_PACK_ROW_LENGTH: if (!_mesa_is_desktop_gl(ctx) && !_mesa_is_gles3(ctx)) goto invalid_enum_error; - if (param<0) { - _mesa_error( ctx, GL_INVALID_VALUE, "glPixelStore(param)" ); - return; - } - if (ctx->Pack.RowLength == param) - return; - ctx->Pack.RowLength = param; - break; + if (param<0) + goto invalid_value_error; + ctx->Pack.RowLength = param; + break; case GL_PACK_IMAGE_HEIGHT: if (!_mesa_is_desktop_gl(ctx) && !_mesa_is_gles3(ctx)) goto invalid_enum_error; - if (param<0) { - _mesa_error( ctx, GL_INVALID_VALUE, "glPixelStore(param)" ); - return; - } - if (ctx->Pack.ImageHeight == param) - return; - ctx->Pack.ImageHeight = param; + if (param<0) + goto invalid_value_error; + ctx->Pack.ImageHeight = param; break; case GL_PACK_SKIP_PIXELS: if (!_mesa_is_desktop_gl(ctx) && !_mesa_is_gles3(ctx)) goto invalid_enum_error; - if (param<0) { - _mesa_error( ctx, GL_INVALID_VALUE, "glPixelStore(param)" ); - return; - } - if (ctx->Pack.SkipPixels == param) - return; - ctx->Pack.SkipPixels = param; - break; + if (param<0) + goto invalid_value_error; + ctx->Pack.SkipPixels = param; + break; case GL_PACK_SKIP_ROWS: if (!_mesa_is_desktop_gl(ctx) && !_mesa_is_gles3(ctx)) goto invalid_enum_error; - if (param<0) { - _mesa_error( ctx, GL_INVALID_VALUE, "glPixelStore(param)" ); - return; - } - if (ctx->Pack.SkipRows == param) - return; - ctx->Pack.SkipRows = param; - break; + if (param<0) + goto invalid_value_error; + ctx->Pack.SkipRows = param; + break; case GL_PACK_SKIP_IMAGES: if (!_mesa_is_desktop_gl(ctx) && !_mesa_is_gles3(ctx)) goto invalid_enum_error; - if (param<0) { - _mesa_error( ctx, GL_INVALID_VALUE, "glPixelStore(param)" ); - return; - } - if (ctx->Pack.SkipImages == param) - return; - ctx->Pack.SkipImages = param; - break; + if (param<0) + goto invalid_value_error; + ctx->Pack.SkipImages = param; + break; case GL_PACK_ALIGNMENT: - if (param!=1 && param!=2 && param!=4 && param!=8) { - _mesa_error( ctx, GL_INVALID_VALUE, "glPixelStore(param)" ); - return; - } - if (ctx->Pack.Alignment == param) - return; - ctx->Pack.Alignment = param; - break; + if (param!=1 && param!=2 && param!=4 && param!=8) + goto invalid_value_error; + ctx->Pack.Alignment = param; + break; case GL_PACK_INVERT_MESA: - if (!_mesa_is_desktop_gl(ctx)) + if (!_mesa_is_desktop_gl(ctx) || !ctx->Extensions.MESA_pack_invert) goto invalid_enum_error; - if (!ctx->Extensions.MESA_pack_invert) { - _mesa_error( ctx, GL_INVALID_ENUM, "glPixelstore(pname)" ); - return; - } - if (ctx->Pack.Invert == param) - return; ctx->Pack.Invert = param; break; + case GL_PACK_COMPRESSED_BLOCK_WIDTH: + if (!_mesa_is_desktop_gl(ctx)) + goto invalid_enum_error; + if (param<0) + goto invalid_value_error; + ctx->Pack.CompressedBlockWidth = param; + break; + case GL_PACK_COMPRESSED_BLOCK_HEIGHT: + if (!_mesa_is_desktop_gl(ctx)) + goto invalid_enum_error; + if (param<0) + goto invalid_value_error; + ctx->Pack.CompressedBlockHeight = param; + break; + case GL_PACK_COMPRESSED_BLOCK_DEPTH: + if (!_mesa_is_desktop_gl(ctx)) + goto invalid_enum_error; + if (param<0) + goto invalid_value_error; + ctx->Pack.CompressedBlockDepth = param; + break; + case GL_PACK_COMPRESSED_BLOCK_SIZE: + if (!_mesa_is_desktop_gl(ctx)) + goto invalid_enum_error; + if (param<0) + goto invalid_value_error; + ctx->Pack.CompressedBlockSize = param; + break; case GL_UNPACK_SWAP_BYTES: if (!_mesa_is_desktop_gl(ctx)) goto invalid_enum_error; - if (param == (GLint)ctx->Unpack.SwapBytes) - return; - if ((GLint)ctx->Unpack.SwapBytes == param) - return; - ctx->Unpack.SwapBytes = param ? GL_TRUE : GL_FALSE; + ctx->Unpack.SwapBytes = param ? GL_TRUE : GL_FALSE; break; case GL_UNPACK_LSB_FIRST: if (!_mesa_is_desktop_gl(ctx)) goto invalid_enum_error; - if (param == (GLint)ctx->Unpack.LsbFirst) - return; - if ((GLint)ctx->Unpack.LsbFirst == param) - return; - ctx->Unpack.LsbFirst = param ? GL_TRUE : GL_FALSE; - break; + ctx->Unpack.LsbFirst = param ? GL_TRUE : GL_FALSE; + break; case GL_UNPACK_ROW_LENGTH: if (ctx->API == API_OPENGLES) goto invalid_enum_error; - if (param<0) { - _mesa_error( ctx, GL_INVALID_VALUE, "glPixelStore(param)" ); - return; - } - if (ctx->Unpack.RowLength == param) - return; - ctx->Unpack.RowLength = param; - break; + if (param<0) + goto invalid_value_error; + ctx->Unpack.RowLength = param; + break; case GL_UNPACK_IMAGE_HEIGHT: if (!_mesa_is_desktop_gl(ctx) && !_mesa_is_gles3(ctx)) goto invalid_enum_error; - if (param<0) { - _mesa_error( ctx, GL_INVALID_VALUE, "glPixelStore(param)" ); - return; - } - if (ctx->Unpack.ImageHeight == param) - return; - - ctx->Unpack.ImageHeight = param; + if (param<0) + goto invalid_value_error; + ctx->Unpack.ImageHeight = param; break; case GL_UNPACK_SKIP_PIXELS: if (ctx->API == API_OPENGLES) goto invalid_enum_error; - if (param<0) { - _mesa_error( ctx, GL_INVALID_VALUE, "glPixelStore(param)" ); - return; - } - if (ctx->Unpack.SkipPixels == param) - return; - ctx->Unpack.SkipPixels = param; - break; + if (param<0) + goto invalid_value_error; + ctx->Unpack.SkipPixels = param; + break; case GL_UNPACK_SKIP_ROWS: if (ctx->API == API_OPENGLES) goto invalid_enum_error; - if (param<0) { - _mesa_error( ctx, GL_INVALID_VALUE, "glPixelStore(param)" ); - return; - } - if (ctx->Unpack.SkipRows == param) - return; - ctx->Unpack.SkipRows = param; - break; + if (param<0) + goto invalid_value_error; + ctx->Unpack.SkipRows = param; + break; case GL_UNPACK_SKIP_IMAGES: if (!_mesa_is_desktop_gl(ctx) && !_mesa_is_gles3(ctx)) goto invalid_enum_error; - if (param < 0) { - _mesa_error( ctx, GL_INVALID_VALUE, "glPixelStore(param)" ); - return; - } - if (ctx->Unpack.SkipImages == param) - return; - ctx->Unpack.SkipImages = param; - break; + if (param < 0) + goto invalid_value_error; + ctx->Unpack.SkipImages = param; + break; case GL_UNPACK_ALIGNMENT: - if (param!=1 && param!=2 && param!=4 && param!=8) { - _mesa_error( ctx, GL_INVALID_VALUE, "glPixelStore" ); - return; - } - if (ctx->Unpack.Alignment == param) - return; - ctx->Unpack.Alignment = param; - break; + if (param!=1 && param!=2 && param!=4 && param!=8) + goto invalid_value_error; + ctx->Unpack.Alignment = param; + break; + case GL_UNPACK_COMPRESSED_BLOCK_WIDTH: + if (!_mesa_is_desktop_gl(ctx)) + goto invalid_enum_error; + if (param<0) + goto invalid_value_error; + ctx->Unpack.CompressedBlockWidth = param; + break; + case GL_UNPACK_COMPRESSED_BLOCK_HEIGHT: + if (!_mesa_is_desktop_gl(ctx)) + goto invalid_enum_error; + if (param<0) + goto invalid_value_error; + ctx->Unpack.CompressedBlockHeight = param; + break; + case GL_UNPACK_COMPRESSED_BLOCK_DEPTH: + if (!_mesa_is_desktop_gl(ctx)) + goto invalid_enum_error; + if (param<0) + goto invalid_value_error; + ctx->Unpack.CompressedBlockDepth = param; + break; + case GL_UNPACK_COMPRESSED_BLOCK_SIZE: + if (!_mesa_is_desktop_gl(ctx)) + goto invalid_enum_error; + if (param<0) + goto invalid_value_error; + ctx->Unpack.CompressedBlockSize = param; + break; default: goto invalid_enum_error; } @@ -224,6 +213,10 @@ _mesa_PixelStorei( GLenum pname, GLint param ) invalid_enum_error: _mesa_error( ctx, GL_INVALID_ENUM, "glPixelStore" ); return; + +invalid_value_error: + _mesa_error( ctx, GL_INVALID_VALUE, "glPixelStore(param)" ); + return; } @@ -251,6 +244,10 @@ _mesa_init_pixelstore( struct gl_context *ctx ) ctx->Pack.SwapBytes = GL_FALSE; ctx->Pack.LsbFirst = GL_FALSE; ctx->Pack.Invert = GL_FALSE; + ctx->Pack.CompressedBlockWidth = 0; + ctx->Pack.CompressedBlockHeight = 0; + ctx->Pack.CompressedBlockDepth = 0; + ctx->Pack.CompressedBlockSize = 0; _mesa_reference_buffer_object(ctx, &ctx->Pack.BufferObj, ctx->Shared->NullBufferObj); ctx->Unpack.Alignment = 4; @@ -262,6 +259,10 @@ _mesa_init_pixelstore( struct gl_context *ctx ) ctx->Unpack.SwapBytes = GL_FALSE; ctx->Unpack.LsbFirst = GL_FALSE; ctx->Unpack.Invert = GL_FALSE; + ctx->Unpack.CompressedBlockWidth = 0; + ctx->Unpack.CompressedBlockHeight = 0; + ctx->Unpack.CompressedBlockDepth = 0; + ctx->Unpack.CompressedBlockSize = 0; _mesa_reference_buffer_object(ctx, &ctx->Unpack.BufferObj, ctx->Shared->NullBufferObj); diff --git a/mesalib/src/mesa/main/shaderapi.c b/mesalib/src/mesa/main/shaderapi.c index 28739daeb..2ec2444da 100644 --- a/mesalib/src/mesa/main/shaderapi.c +++ b/mesalib/src/mesa/main/shaderapi.c @@ -1392,7 +1392,7 @@ _mesa_LinkProgram(GLhandleARB programObj) static GLcharARB * read_shader(const char *fname) { - const int max = 50*1000; + int shader_size = 0; FILE *f = fopen(fname, "r"); GLcharARB *buffer, *shader; int len; @@ -1401,8 +1401,19 @@ read_shader(const char *fname) return NULL; } - buffer = malloc(max); - len = fread(buffer, 1, max, f); + /* allocate enough room for the entire shader */ + fseek(f, 0, SEEK_END); + shader_size = ftell(f); + rewind(f); + assert(shader_size); + + /* add one for terminating zero */ + shader_size++; + + buffer = malloc(shader_size); + assert(buffer); + + len = fread(buffer, 1, shader_size, f); buffer[len] = 0; fclose(f); diff --git a/mesalib/src/mesa/main/shaderobj.c b/mesalib/src/mesa/main/shaderobj.c index b0f0bfa91..c6e852c87 100644 --- a/mesalib/src/mesa/main/shaderobj.c +++ b/mesalib/src/mesa/main/shaderobj.c @@ -248,6 +248,7 @@ _mesa_init_shader_program(struct gl_context *ctx, struct gl_shader_program *prog prog->Geom.VerticesOut = 0; prog->Geom.InputType = GL_TRIANGLES; prog->Geom.OutputType = GL_TRIANGLE_STRIP; + prog->Geom.UsesEndPrimitive = false; prog->TransformFeedback.BufferMode = GL_INTERLEAVED_ATTRIBS; diff --git a/mesalib/src/mesa/main/texgetimage.c b/mesalib/src/mesa/main/texgetimage.c index 1ac707d13..8c0d3a18e 100644 --- a/mesalib/src/mesa/main/texgetimage.c +++ b/mesalib/src/mesa/main/texgetimage.c @@ -43,6 +43,7 @@ #include "texcompress.h" #include "texgetimage.h" #include "teximage.h" +#include "texstore.h" @@ -686,56 +687,62 @@ _mesa_get_compressed_teximage(struct gl_context *ctx, struct gl_texture_image *texImage, GLvoid *img) { - const GLuint row_stride = - _mesa_format_row_stride(texImage->TexFormat, texImage->Width); - GLuint i; - GLubyte *src; - GLint srcRowStride; + const GLuint dimensions = + _mesa_get_texture_dimensions(texImage->TexObject->Target); + struct compressed_pixelstore store; + GLuint i, slice; + GLubyte *dest; + + _mesa_compute_compressed_pixelstore(dimensions, texImage, + texImage->Width, texImage->Height, + texImage->Depth, + &ctx->Pack, + &store); if (_mesa_is_bufferobj(ctx->Pack.BufferObj)) { /* pack texture image into a PBO */ - GLubyte *buf = (GLubyte *) + dest = (GLubyte *) ctx->Driver.MapBufferRange(ctx, 0, ctx->Pack.BufferObj->Size, GL_MAP_WRITE_BIT, ctx->Pack.BufferObj, MAP_INTERNAL); - if (!buf) { + if (!dest) { /* out of memory or other unexpected error */ _mesa_error(ctx, GL_OUT_OF_MEMORY, "glGetCompresssedTexImage(map PBO failed)"); return; } - img = ADD_POINTERS(buf, img); + dest = ADD_POINTERS(dest, img); + } else { + dest = img; } - /* map src texture buffer */ - ctx->Driver.MapTextureImage(ctx, texImage, 0, - 0, 0, texImage->Width, texImage->Height, - GL_MAP_READ_BIT, &src, &srcRowStride); + dest += store.SkipBytes; - if (src) { - /* no pixelstore or pixel transfer, but respect stride */ + for (slice = 0; slice < store.CopySlices; slice++) { + GLint srcRowStride; + GLubyte *src; - if (row_stride == srcRowStride) { - const GLuint size = _mesa_format_image_size(texImage->TexFormat, - texImage->Width, - texImage->Height, - texImage->Depth); - memcpy(img, src, size); - } - else { - GLuint bw, bh; - _mesa_get_format_block_size(texImage->TexFormat, &bw, &bh); - for (i = 0; i < (texImage->Height + bh - 1) / bh; i++) { - memcpy((GLubyte *)img + i * row_stride, - (GLubyte *)src + i * srcRowStride, - row_stride); + /* map src texture buffer */ + ctx->Driver.MapTextureImage(ctx, texImage, 0, + 0, 0, texImage->Width, texImage->Height, + GL_MAP_READ_BIT, &src, &srcRowStride); + + if (src) { + + for (i = 0; i < store.CopyRowsPerSlice; i++) { + memcpy(dest, src, store.CopyBytesPerRow); + dest += store.TotalBytesPerRow; + src += srcRowStride; } - } - ctx->Driver.UnmapTextureImage(ctx, texImage, 0); - } - else { - _mesa_error(ctx, GL_OUT_OF_MEMORY, "glGetCompresssedTexImage"); + ctx->Driver.UnmapTextureImage(ctx, texImage, 0); + + /* Advance to next slice */ + dest += store.TotalBytesPerRow * (store.TotalRowsPerSlice - store.CopyRowsPerSlice); + + } else { + _mesa_error(ctx, GL_OUT_OF_MEMORY, "glGetCompresssedTexImage"); + } } if (_mesa_is_bufferobj(ctx->Pack.BufferObj)) { @@ -963,7 +970,7 @@ getcompressedteximage_error_check(struct gl_context *ctx, GLenum target, struct gl_texture_object *texObj; struct gl_texture_image *texImage; const GLint maxLevels = _mesa_max_texture_levels(ctx, target); - GLuint compressedSize; + GLuint compressedSize, dimensions; if (!legal_getteximage_target(ctx, target)) { _mesa_error(ctx, GL_INVALID_ENUM, "glGetCompressedTexImage(target=0x%x)", @@ -1004,6 +1011,14 @@ getcompressedteximage_error_check(struct gl_context *ctx, GLenum target, texImage->Height, texImage->Depth); + /* Check for invalid pixel storage modes */ + dimensions = _mesa_get_texture_dimensions(texImage->TexObject->Target); + if (!_mesa_compressed_texture_pixel_storage_error_check(ctx, dimensions, + &ctx->Pack, + "glGetCompressedTexImageARB")) { + return GL_TRUE; + } + if (!_mesa_is_bufferobj(ctx->Pack.BufferObj)) { /* do bounds checking on writing to client memory */ if (clientMemSize < (GLsizei) compressedSize) { diff --git a/mesalib/src/mesa/main/teximage.c b/mesalib/src/mesa/main/teximage.c index 845ba8014..cab29c35d 100644 --- a/mesalib/src/mesa/main/teximage.c +++ b/mesalib/src/mesa/main/teximage.c @@ -2242,6 +2242,36 @@ texture_error_check( struct gl_context *ctx, } +bool +_mesa_compressed_texture_pixel_storage_error_check(struct gl_context *ctx, + GLint dimensions, + struct gl_pixelstore_attrib *packing, + const char *caller) +{ + if (!_mesa_is_desktop_gl(ctx) || !packing->CompressedBlockSize) + return true; + + if (packing->CompressedBlockWidth && packing->SkipPixels % packing->CompressedBlockWidth) { + _mesa_error(ctx, GL_INVALID_OPERATION, + "%s(skip-pixels %% block-width)", caller); + return false; + } + + if (dimensions > 1 && packing->CompressedBlockHeight && packing->SkipRows % packing->CompressedBlockHeight) { + _mesa_error(ctx, GL_INVALID_OPERATION, + "%s(skip-rows %% block-height)", caller); + return false; + } + + if (dimensions > 2 && packing->CompressedBlockDepth && packing->SkipImages % packing->CompressedBlockDepth) { + _mesa_error(ctx, GL_INVALID_OPERATION, + "%s(skip-images %% block-depth)", caller); + return false; + } + + return true; +} + /** * Error checking for glCompressedTexImage[123]D(). * Note that the width, height and depth values are not fully error checked @@ -2343,6 +2373,13 @@ compressed_texture_error_check(struct gl_context *ctx, GLint dimensions, goto error; } + /* Check for invalid pixel storage modes */ + if (!_mesa_compressed_texture_pixel_storage_error_check(ctx, dimensions, + &ctx->Unpack, + "glCompressedTexImage")) { + return GL_FALSE; + } + /* check image size in bytes */ if (expectedSize != imageSize) { /* Per GL_ARB_texture_compression: GL_INVALID_VALUE is generated [...] @@ -3844,7 +3881,7 @@ compressed_subtexture_error_check(struct gl_context *ctx, GLint dims, } if (!targetOK) { - _mesa_error(ctx, GL_INVALID_ENUM, "glCompressedTexImage%uD(target)", + _mesa_error(ctx, GL_INVALID_ENUM, "glCompressedTexSubImage%uD(target)", dims); return GL_TRUE; } @@ -3857,14 +3894,22 @@ compressed_subtexture_error_check(struct gl_context *ctx, GLint dims, } if (level < 0 || level >= _mesa_max_texture_levels(ctx, target)) { - _mesa_error(ctx, GL_INVALID_VALUE, "glCompressedTexImage%uD(level=%d)", + _mesa_error(ctx, GL_INVALID_VALUE, "glCompressedTexSubImage%uD(level=%d)", dims, level); return GL_TRUE; } + /* Check for invalid pixel storage modes */ + if (!_mesa_compressed_texture_pixel_storage_error_check(ctx, dims, + &ctx->Unpack, + "glCompressedTexSubImage")) { + return GL_FALSE; + } + + expectedSize = compressed_tex_size(width, height, depth, format); if (expectedSize != imageSize) { - _mesa_error(ctx, GL_INVALID_VALUE, "glCompressedTexImage%uD(size=%d)", + _mesa_error(ctx, GL_INVALID_VALUE, "glCompressedTexSubImage%uD(size=%d)", dims, imageSize); return GL_TRUE; } diff --git a/mesalib/src/mesa/main/teximage.h b/mesalib/src/mesa/main/teximage.h index 51d94d17e..dd1504b40 100644 --- a/mesalib/src/mesa/main/teximage.h +++ b/mesalib/src/mesa/main/teximage.h @@ -326,6 +326,12 @@ _mesa_TexStorage3DMultisample(GLenum target, GLsizei samples, GLsizei height, GLsizei depth, GLboolean fixedsamplelocations); +bool +_mesa_compressed_texture_pixel_storage_error_check(struct gl_context *ctx, + GLint dimensions, + struct gl_pixelstore_attrib *packing, + const char *caller); + /*@}*/ #ifdef __cplusplus diff --git a/mesalib/src/mesa/main/texstore.c b/mesalib/src/mesa/main/texstore.c index 764214669..cb81f3fde 100644 --- a/mesalib/src/mesa/main/texstore.c +++ b/mesalib/src/mesa/main/texstore.c @@ -4195,6 +4195,61 @@ _mesa_store_compressed_teximage(struct gl_context *ctx, GLuint dims, } +void +_mesa_compute_compressed_pixelstore(GLuint dims, struct gl_texture_image *texImage, + GLsizei width, GLsizei height, GLsizei depth, + const struct gl_pixelstore_attrib *packing, + struct compressed_pixelstore *store) +{ + GLuint bw, bh; + const mesa_format texFormat = texImage->TexFormat; + + _mesa_get_format_block_size(texFormat, &bw, &bh); + + store->SkipBytes = 0; + store->TotalBytesPerRow = store->CopyBytesPerRow = + _mesa_format_row_stride(texFormat, width); + store->TotalRowsPerSlice = store->CopyRowsPerSlice = + (height + bh - 1) / bh; + store->CopySlices = depth; + + if (packing->CompressedBlockWidth && + packing->CompressedBlockSize) { + + bw = packing->CompressedBlockWidth; + + if (packing->RowLength) { + store->TotalBytesPerRow = packing->CompressedBlockSize * + (packing->RowLength + bw - 1) / bw; + } + + store->SkipBytes += packing->SkipPixels * packing->CompressedBlockSize / bw; + } + + if (dims > 1 && packing->CompressedBlockHeight && + packing->CompressedBlockSize) { + + bh = packing->CompressedBlockHeight; + + store->SkipBytes += packing->SkipRows * store->TotalBytesPerRow / bh; + store->CopyRowsPerSlice = (height + bh - 1) / bh; /* rows in blocks */ + + if (packing->ImageHeight) { + store->TotalRowsPerSlice = (packing->ImageHeight + bh - 1) / bh; + } + } + + if (dims > 2 && packing->CompressedBlockDepth && + packing->CompressedBlockSize) { + + int bd = packing->CompressedBlockDepth; + + store->SkipBytes += packing->SkipImages * store->TotalBytesPerRow * + store->TotalRowsPerSlice / bd; + } +} + + /** * Fallback for Driver.CompressedTexSubImage() */ @@ -4206,20 +4261,19 @@ _mesa_store_compressed_texsubimage(struct gl_context *ctx, GLuint dims, GLenum format, GLsizei imageSize, const GLvoid *data) { - GLint bytesPerRow, dstRowStride, srcRowStride; - GLint i, rows; + struct compressed_pixelstore store; + GLint dstRowStride; + GLint i, slice; GLubyte *dstMap; const GLubyte *src; - const mesa_format texFormat = texImage->TexFormat; - GLuint bw, bh; - GLint slice; if (dims == 1) { _mesa_problem(ctx, "Unexpected 1D compressed texsubimage call"); return; } - _mesa_get_format_block_size(texFormat, &bw, &bh); + _mesa_compute_compressed_pixelstore(dims, texImage, width, height, depth, + &ctx->Unpack, &store); /* get pointer to src pixels (may be in a pbo which we'll map here) */ data = _mesa_validate_pbo_compressed_teximage(ctx, dims, imageSize, data, @@ -4228,10 +4282,9 @@ _mesa_store_compressed_texsubimage(struct gl_context *ctx, GLuint dims, if (!data) return; - srcRowStride = _mesa_format_row_stride(texFormat, width); - src = (const GLubyte *) data; + src = (const GLubyte *) data + store.SkipBytes; - for (slice = 0; slice < depth; slice++) { + for (slice = 0; slice < store.CopySlices; slice++) { /* Map dest texture buffer */ ctx->Driver.MapTextureImage(ctx, texImage, slice + zoffset, xoffset, yoffset, width, height, @@ -4239,17 +4292,18 @@ _mesa_store_compressed_texsubimage(struct gl_context *ctx, GLuint dims, &dstMap, &dstRowStride); if (dstMap) { - bytesPerRow = srcRowStride; /* bytes per row of blocks */ - rows = (height + bh - 1) / bh; /* rows in blocks */ /* copy rows of blocks */ - for (i = 0; i < rows; i++) { - memcpy(dstMap, src, bytesPerRow); + for (i = 0; i < store.CopyRowsPerSlice; i++) { + memcpy(dstMap, src, store.CopyBytesPerRow); dstMap += dstRowStride; - src += srcRowStride; + src += store.TotalBytesPerRow; } ctx->Driver.UnmapTextureImage(ctx, texImage, slice + zoffset); + + /* advance to next slice */ + src += store.TotalBytesPerRow * (store.TotalRowsPerSlice - store.CopyRowsPerSlice); } else { _mesa_error(ctx, GL_OUT_OF_MEMORY, "glCompressedTexSubImage%uD", diff --git a/mesalib/src/mesa/main/texstore.h b/mesalib/src/mesa/main/texstore.h index 490f9f5e0..c4cfffde6 100644 --- a/mesalib/src/mesa/main/texstore.h +++ b/mesalib/src/mesa/main/texstore.h @@ -132,4 +132,21 @@ _mesa_store_compressed_texsubimage(struct gl_context *ctx, GLuint dims, GLsizei imageSize, const GLvoid *data); +struct compressed_pixelstore { + int SkipBytes; + int CopyBytesPerRow; + int CopyRowsPerSlice; + int TotalBytesPerRow; + int TotalRowsPerSlice; + int CopySlices; +}; + + +extern void +_mesa_compute_compressed_pixelstore(GLuint dims, struct gl_texture_image *texImage, + GLsizei width, GLsizei height, GLsizei depth, + const struct gl_pixelstore_attrib *packing, + struct compressed_pixelstore *store); + + #endif diff --git a/mesalib/src/mesa/main/uniform_query.cpp b/mesalib/src/mesa/main/uniform_query.cpp index 5f1af0873..480bc6f16 100644 --- a/mesalib/src/mesa/main/uniform_query.cpp +++ b/mesalib/src/mesa/main/uniform_query.cpp @@ -253,6 +253,21 @@ validate_uniform_parameters(struct gl_context *ctx, return false; } + /* If the driver storage pointer in remap table is -1, we ignore silently. + * + * GL_ARB_explicit_uniform_location spec says: + * "What happens if Uniform* is called with an explicitly defined + * uniform location, but that uniform is deemed inactive by the + * linker? + * + * RESOLVED: The call is ignored for inactive uniform variables and + * no error is generated." + * + */ + if (shProg->UniformRemapTable[location] == + INACTIVE_UNIFORM_EXPLICIT_LOCATION) + return false; + _mesa_uniform_split_location_offset(shProg, location, loc, array_index); if (shProg->UniformStorage[*loc].array_elements == 0 && count > 1) { diff --git a/mesalib/src/mesa/main/uniforms.c b/mesalib/src/mesa/main/uniforms.c index 1daade428..f450173af 100644 --- a/mesalib/src/mesa/main/uniforms.c +++ b/mesalib/src/mesa/main/uniforms.c @@ -112,7 +112,7 @@ _mesa_uniform_attach_driver_storage(struct gl_uniform_storage *uni, uni->driver_storage[uni->num_driver_storage].element_stride = element_stride; uni->driver_storage[uni->num_driver_storage].vector_stride = vector_stride; - uni->driver_storage[uni->num_driver_storage].format = (uint8_t) format; + uni->driver_storage[uni->num_driver_storage].format = format; uni->driver_storage[uni->num_driver_storage].data = data; uni->num_driver_storage++; diff --git a/mesalib/src/mesa/program/program.c b/mesalib/src/mesa/program/program.c index b7332fccf..988def1a3 100644 --- a/mesalib/src/mesa/program/program.c +++ b/mesalib/src/mesa/program/program.c @@ -552,6 +552,7 @@ _mesa_clone_program(struct gl_context *ctx, const struct gl_program *prog) gpc->InputType = gp->InputType; gpc->Invocations = gp->Invocations; gpc->OutputType = gp->OutputType; + gpc->UsesEndPrimitive = gp->UsesEndPrimitive; } break; default: diff --git a/mesalib/src/mesa/state_tracker/st_atom_sampler.c b/mesalib/src/mesa/state_tracker/st_atom_sampler.c index 3929251f8..17b536bf5 100644 --- a/mesalib/src/mesa/state_tracker/st_atom_sampler.c +++ b/mesalib/src/mesa/state_tracker/st_atom_sampler.c @@ -160,11 +160,8 @@ convert_sampler(struct st_context *st, sampler->lod_bias = ctx->Texture.Unit[texUnit].LodBias + msamp->LodBias; - sampler->min_lod = CLAMP(msamp->MinLod, - 0.0f, - (GLfloat) texobj->MaxLevel - texobj->BaseLevel); - sampler->max_lod = MIN2((GLfloat) texobj->MaxLevel - texobj->BaseLevel, - msamp->MaxLod); + sampler->min_lod = MAX2(msamp->MinLod, 0.0f); + sampler->max_lod = msamp->MaxLod; if (sampler->max_lod < sampler->min_lod) { /* The GL spec doesn't seem to specify what to do in this case. * Swap the values. diff --git a/mesalib/src/mesa/state_tracker/st_atom_texture.c b/mesalib/src/mesa/state_tracker/st_atom_texture.c index e2d26ee24..2e10bc3e2 100644 --- a/mesalib/src/mesa/state_tracker/st_atom_texture.c +++ b/mesalib/src/mesa/state_tracker/st_atom_texture.c @@ -212,6 +212,12 @@ check_sampler_swizzle(const struct st_texture_object *stObj, } +static unsigned last_level(struct st_texture_object *stObj) +{ + return MIN2(stObj->base._MaxLevel, stObj->pt->last_level); +} + + static struct pipe_sampler_view * st_create_texture_sampler_view_from_stobj(struct pipe_context *pipe, struct st_texture_object *stObj, @@ -244,6 +250,8 @@ st_create_texture_sampler_view_from_stobj(struct pipe_context *pipe, templ.u.buf.last_element = f + (n - 1); } else { templ.u.tex.first_level = stObj->base.BaseLevel; + templ.u.tex.last_level = last_level(stObj); + assert(templ.u.tex.first_level <= templ.u.tex.last_level); } if (swizzle != SWIZZLE_NOOP) { @@ -279,7 +287,8 @@ st_get_texture_sampler_view_from_stobj(struct st_context *st, if (*sv) { if (check_sampler_swizzle(stObj, *sv) || (format != (*sv)->format) || - stObj->base.BaseLevel != (*sv)->u.tex.first_level) { + stObj->base.BaseLevel != (*sv)->u.tex.first_level || + last_level(stObj) != (*sv)->u.tex.last_level) { pipe_sampler_view_reference(sv, NULL); } } @@ -434,7 +443,7 @@ update_geometry_textures(struct st_context *st) update_textures(st, PIPE_SHADER_GEOMETRY, &ctx->GeometryProgram._Current->Base, - ctx->Const.Program[MESA_SHADER_FRAGMENT].MaxTextureImageUnits, + ctx->Const.Program[MESA_SHADER_GEOMETRY].MaxTextureImageUnits, st->state.sampler_views[PIPE_SHADER_GEOMETRY], &st->state.num_sampler_views[PIPE_SHADER_GEOMETRY]); } diff --git a/mesalib/src/mesa/state_tracker/st_extensions.c b/mesalib/src/mesa/state_tracker/st_extensions.c index 12ba82df3..e93804689 100644 --- a/mesalib/src/mesa/state_tracker/st_extensions.c +++ b/mesalib/src/mesa/state_tracker/st_extensions.c @@ -543,6 +543,7 @@ void st_init_extensions(struct st_context *st) ctx->Extensions.ARB_ES2_compatibility = GL_TRUE; ctx->Extensions.ARB_draw_elements_base_vertex = GL_TRUE; ctx->Extensions.ARB_explicit_attrib_location = GL_TRUE; + ctx->Extensions.ARB_explicit_uniform_location = GL_TRUE; ctx->Extensions.ARB_fragment_coord_conventions = GL_TRUE; ctx->Extensions.ARB_fragment_program = GL_TRUE; ctx->Extensions.ARB_fragment_shader = GL_TRUE; @@ -630,6 +631,7 @@ void st_init_extensions(struct st_context *st) ctx->Extensions.ARB_shading_language_packing = GL_TRUE; ctx->Extensions.OES_depth_texture_cube_map = GL_TRUE; ctx->Extensions.ARB_shading_language_420pack = GL_TRUE; + ctx->Extensions.ARB_texture_query_levels = GL_TRUE; if (!st->options.disable_shader_bit_encoding) { ctx->Extensions.ARB_shader_bit_encoding = GL_TRUE; diff --git a/mesalib/src/mesa/state_tracker/st_glsl_to_tgsi.cpp b/mesalib/src/mesa/state_tracker/st_glsl_to_tgsi.cpp index 739e1089e..cac1e0fe2 100644 --- a/mesalib/src/mesa/state_tracker/st_glsl_to_tgsi.cpp +++ b/mesalib/src/mesa/state_tracker/st_glsl_to_tgsi.cpp @@ -2779,7 +2779,9 @@ glsl_to_tgsi_visitor::visit(ir_call *ir) void glsl_to_tgsi_visitor::visit(ir_texture *ir) { - st_src_reg result_src, coord, cube_sc, lod_info, projector, dx, dy, offset[MAX_GLSL_TEXTURE_OFFSET], sample_index, component; + st_src_reg result_src, coord, cube_sc, lod_info, projector, dx, dy; + st_src_reg offset[MAX_GLSL_TEXTURE_OFFSET], sample_index, component; + st_src_reg levels_src; st_dst_reg result_dst, coord_dst, cube_sc_dst; glsl_to_tgsi_instruction *inst = NULL; unsigned opcode = TGSI_OPCODE_NOP; @@ -2860,6 +2862,11 @@ glsl_to_tgsi_visitor::visit(ir_texture *ir) ir->lod_info.lod->accept(this); lod_info = this->result; break; + case ir_query_levels: + opcode = TGSI_OPCODE_TXQ; + lod_info = st_src_reg(PROGRAM_IMMEDIATE, 0, GLSL_TYPE_INT); + levels_src = get_temp(ir->type); + break; case ir_txf: opcode = TGSI_OPCODE_TXF; ir->lod_info.lod->accept(this); @@ -2896,9 +2903,6 @@ glsl_to_tgsi_visitor::visit(ir_texture *ir) case ir_lod: opcode = TGSI_OPCODE_LODQ; break; - case ir_query_levels: - assert(!"Unexpected ir_query_levels opcode"); - break; } if (ir->projector) { @@ -2995,9 +2999,16 @@ glsl_to_tgsi_visitor::visit(ir_texture *ir) if (opcode == TGSI_OPCODE_TXD) inst = emit(ir, opcode, result_dst, coord, dx, dy); - else if (opcode == TGSI_OPCODE_TXQ) - inst = emit(ir, opcode, result_dst, lod_info); - else if (opcode == TGSI_OPCODE_TXF) { + else if (opcode == TGSI_OPCODE_TXQ) { + if (ir->op == ir_query_levels) { + /* the level is stored in W */ + inst = emit(ir, opcode, st_dst_reg(levels_src), lod_info); + result_dst.writemask = WRITEMASK_X; + levels_src.swizzle = SWIZZLE_WWWW; + emit(ir, TGSI_OPCODE_MOV, result_dst, levels_src); + } else + inst = emit(ir, opcode, result_dst, lod_info); + } else if (opcode == TGSI_OPCODE_TXF) { inst = emit(ir, opcode, result_dst, coord); } else if (opcode == TGSI_OPCODE_TXL2 || opcode == TGSI_OPCODE_TXB2) { inst = emit(ir, opcode, result_dst, coord, lod_info); diff --git a/mesalib/src/mesa/state_tracker/st_program.c b/mesalib/src/mesa/state_tracker/st_program.c index 26eb9786d..1df411c3b 100644 --- a/mesalib/src/mesa/state_tracker/st_program.c +++ b/mesalib/src/mesa/state_tracker/st_program.c @@ -572,6 +572,11 @@ st_translate_fragment_program(struct st_context *st, input_semantic_index[slot] = 0; interpMode[slot] = TGSI_INTERPOLATE_CONSTANT; break; + case VARYING_SLOT_LAYER: + input_semantic_name[slot] = TGSI_SEMANTIC_LAYER; + input_semantic_index[slot] = 0; + interpMode[slot] = TGSI_INTERPOLATE_CONSTANT; + break; case VARYING_SLOT_VIEWPORT: input_semantic_name[slot] = TGSI_SEMANTIC_VIEWPORT_INDEX; input_semantic_index[slot] = 0; diff --git a/mesalib/src/mesa/state_tracker/st_texture.c b/mesalib/src/mesa/state_tracker/st_texture.c index 92035e801..c14882142 100644 --- a/mesalib/src/mesa/state_tracker/st_texture.c +++ b/mesalib/src/mesa/state_tracker/st_texture.c @@ -394,6 +394,14 @@ st_texture_image_copy(struct pipe_context *pipe, src_box.width = width; src_box.height = height; src_box.depth = 1; + + if (src->target == PIPE_TEXTURE_1D_ARRAY || + src->target == PIPE_TEXTURE_2D_ARRAY || + src->target == PIPE_TEXTURE_CUBE_ARRAY) { + face = 0; + depth = src->array_size; + } + /* Loop over 3D image slices */ /* could (and probably should) use "true" 3d box here - but drivers can't quite handle it yet */ diff --git a/mesalib/src/mesa/swrast/s_aatriangle.c b/mesalib/src/mesa/swrast/s_aatriangle.c index d670d3154..219282748 100644 --- a/mesalib/src/mesa/swrast/s_aatriangle.c +++ b/mesalib/src/mesa/swrast/s_aatriangle.c @@ -112,20 +112,6 @@ solve_plane(GLfloat x, GLfloat y, const GLfloat plane[4]) /* - * Return 1 / solve_plane(). - */ -static inline GLfloat -solve_plane_recip(GLfloat x, GLfloat y, const GLfloat plane[4]) -{ - const GLfloat denom = plane[3] + plane[0] * x + plane[1] * y; - if (denom == 0.0F) - return 0.0F; - else - return -plane[2] / denom; -} - - -/* * Solve plane and return clamped GLchan value. */ static inline GLchan diff --git a/openssl/ACKNOWLEDGMENTS b/openssl/ACKNOWLEDGMENTS index fb6dd912c..59c6f01f9 100644 --- a/openssl/ACKNOWLEDGMENTS +++ b/openssl/ACKNOWLEDGMENTS @@ -10,13 +10,18 @@ OpenSSL project. We would like to identify and thank the following such sponsors for their past or current significant support of the OpenSSL project: +Major support: + + Qualys http://www.qualys.com/ + Very significant support: - OpenGear: www.opengear.com + OpenGear: http://www.opengear.com/ Significant support: - PSW Group: www.psw.net + PSW Group: http://www.psw.net/ + Acano Ltd. http://acano.com/ Please note that we ask permission to identify sponsors and that some sponsors we consider eligible for inclusion here have requested to remain anonymous. diff --git a/openssl/CHANGES b/openssl/CHANGES index 4fcfd1d4b..d161ecaf2 100644 --- a/openssl/CHANGES +++ b/openssl/CHANGES @@ -2,6 +2,50 @@ OpenSSL CHANGES _______________ + Changes between 1.0.1g and 1.0.1h [5 Jun 2014] + + *) Fix for SSL/TLS MITM flaw. An attacker using a carefully crafted + handshake can force the use of weak keying material in OpenSSL + SSL/TLS clients and servers. + + Thanks to KIKUCHI Masashi (Lepidum Co. Ltd.) for discovering and + researching this issue. (CVE-2014-0224) + [KIKUCHI Masashi, Steve Henson] + + *) Fix DTLS recursion flaw. By sending an invalid DTLS handshake to an + OpenSSL DTLS client the code can be made to recurse eventually crashing + in a DoS attack. + + Thanks to Imre Rad (Search-Lab Ltd.) for discovering this issue. + (CVE-2014-0221) + [Imre Rad, Steve Henson] + + *) Fix DTLS invalid fragment vulnerability. A buffer overrun attack can + be triggered by sending invalid DTLS fragments to an OpenSSL DTLS + client or server. This is potentially exploitable to run arbitrary + code on a vulnerable client or server. + + Thanks to Jri Aedla for reporting this issue. (CVE-2014-0195) + [Jri Aedla, Steve Henson] + + *) Fix bug in TLS code where clients enable anonymous ECDH ciphersuites + are subject to a denial of service attack. + + Thanks to Felix Grbert and Ivan Fratric at Google for discovering + this issue. (CVE-2014-3470) + [Felix Grbert, Ivan Fratric, Steve Henson] + + *) Harmonize version and its documentation. -f flag is used to display + compilation flags. + [mancha <mancha1@zoho.com>] + + *) Fix eckey_priv_encode so it immediately returns an error upon a failure + in i2d_ECPrivateKey. + [mancha <mancha1@zoho.com>] + + *) Fix some double frees. These are not thought to be exploitable. + [mancha <mancha1@zoho.com>] + Changes between 1.0.1f and 1.0.1g [7 Apr 2014] *) A missing bounds check in the handling of the TLS heartbeat extension diff --git a/openssl/NEWS b/openssl/NEWS index ed486d146..d0620414a 100644 --- a/openssl/NEWS +++ b/openssl/NEWS @@ -5,6 +5,14 @@ This file gives a brief overview of the major changes between each OpenSSL release. For more details please read the CHANGES file. + Major changes between OpenSSL 1.0.1g and OpenSSL 1.0.1h [5 Jun 2014] + + o Fix for CVE-2014-0224 + o Fix for CVE-2014-0221 + o Fix for CVE-2014-0195 + o Fix for CVE-2014-3470 + o Fix for CVE-2010-5298 + Major changes between OpenSSL 1.0.1f and OpenSSL 1.0.1g [7 Apr 2014] o Fix for CVE-2014-0160 diff --git a/openssl/README b/openssl/README index 10b74d19d..95c5cd247 100644 --- a/openssl/README +++ b/openssl/README @@ -1,5 +1,5 @@ - OpenSSL 1.0.1g 7 Apr 2014 + OpenSSL 1.0.1h 5 Jun 2014 Copyright (c) 1998-2011 The OpenSSL Project Copyright (c) 1995-1998 Eric A. Young, Tim J. Hudson diff --git a/openssl/apps/enc.c b/openssl/apps/enc.c index 719acc325..19ea3df94 100644 --- a/openssl/apps/enc.c +++ b/openssl/apps/enc.c @@ -331,6 +331,12 @@ bad: setup_engine(bio_err, engine, 0); #endif + if (cipher && EVP_CIPHER_flags(cipher) & EVP_CIPH_FLAG_AEAD_CIPHER) + { + BIO_printf(bio_err, "AEAD ciphers not supported by the enc utility\n"); + goto end; + } + if (md && (dgst=EVP_get_digestbyname(md)) == NULL) { BIO_printf(bio_err,"%s is an unsupported message digest type\n",md); diff --git a/openssl/apps/md4.c b/openssl/apps/md4.c index 7f457b2ab..7f457b2ab 100644..120000 --- a/openssl/apps/md4.c +++ b/openssl/apps/md4.c diff --git a/openssl/apps/ocsp.c b/openssl/apps/ocsp.c index 83c5a7670..767f12c62 100644 --- a/openssl/apps/ocsp.c +++ b/openssl/apps/ocsp.c @@ -127,6 +127,7 @@ int MAIN(int argc, char **argv) ENGINE *e = NULL; char **args; char *host = NULL, *port = NULL, *path = "/"; + char *thost = NULL, *tport = NULL, *tpath = NULL; char *reqin = NULL, *respin = NULL; char *reqout = NULL, *respout = NULL; char *signfile = NULL, *keyfile = NULL; @@ -204,6 +205,12 @@ int MAIN(int argc, char **argv) } else if (!strcmp(*args, "-url")) { + if (thost) + OPENSSL_free(thost); + if (tport) + OPENSSL_free(tport); + if (tpath) + OPENSSL_free(tpath); if (args[1]) { args++; @@ -212,6 +219,9 @@ int MAIN(int argc, char **argv) BIO_printf(bio_err, "Error parsing URL\n"); badarg = 1; } + thost = host; + tport = port; + tpath = path; } else badarg = 1; } @@ -920,12 +930,12 @@ end: sk_X509_pop_free(verify_other, X509_free); sk_CONF_VALUE_pop_free(headers, X509V3_conf_free); - if (use_ssl != -1) - { - OPENSSL_free(host); - OPENSSL_free(port); - OPENSSL_free(path); - } + if (thost) + OPENSSL_free(thost); + if (tport) + OPENSSL_free(tport); + if (tpath) + OPENSSL_free(tpath); OPENSSL_EXIT(ret); } diff --git a/openssl/apps/req.c b/openssl/apps/req.c index 5e034a85e..d41385d70 100644 --- a/openssl/apps/req.c +++ b/openssl/apps/req.c @@ -1489,7 +1489,13 @@ start: #ifdef CHARSET_EBCDIC ebcdic2ascii(buf, buf, i); #endif - if(!req_check_len(i, n_min, n_max)) goto start; + if(!req_check_len(i, n_min, n_max)) + { + if (batch || value) + return 0; + goto start; + } + if (!X509_NAME_add_entry_by_NID(n,nid, chtype, (unsigned char *) buf, -1,-1,mval)) goto err; ret=1; @@ -1548,7 +1554,12 @@ start: #ifdef CHARSET_EBCDIC ebcdic2ascii(buf, buf, i); #endif - if(!req_check_len(i, n_min, n_max)) goto start; + if(!req_check_len(i, n_min, n_max)) + { + if (batch || value) + return 0; + goto start; + } if(!X509_REQ_add1_attr_by_NID(req, nid, chtype, (unsigned char *)buf, -1)) { diff --git a/openssl/apps/s_cb.c b/openssl/apps/s_cb.c index 84c3b447c..146a96079 100644 --- a/openssl/apps/s_cb.c +++ b/openssl/apps/s_cb.c @@ -747,6 +747,10 @@ void MS_CALLBACK tlsext_cb(SSL *s, int client_server, int type, break; #endif + case TLSEXT_TYPE_padding: + extname = "TLS padding"; + break; + default: extname = "unknown"; break; diff --git a/openssl/apps/s_socket.c b/openssl/apps/s_socket.c index 380efdb1b..94eb40f3f 100644 --- a/openssl/apps/s_socket.c +++ b/openssl/apps/s_socket.c @@ -274,7 +274,7 @@ static int init_client_ip(int *sock, unsigned char ip[4], int port, int type) { i=0; i=setsockopt(s,SOL_SOCKET,SO_KEEPALIVE,(char *)&i,sizeof(i)); - if (i < 0) { perror("keepalive"); return(0); } + if (i < 0) { closesocket(s); perror("keepalive"); return(0); } } #endif @@ -450,6 +450,7 @@ redoit: if ((*host=(char *)OPENSSL_malloc(strlen(h1->h_name)+1)) == NULL) { perror("OPENSSL_malloc"); + closesocket(ret); return(0); } BUF_strlcpy(*host,h1->h_name,strlen(h1->h_name)+1); @@ -458,11 +459,13 @@ redoit: if (h2 == NULL) { BIO_printf(bio_err,"gethostbyname failure\n"); + closesocket(ret); return(0); } if (h2->h_addrtype != AF_INET) { BIO_printf(bio_err,"gethostbyname addr is not AF_INET\n"); + closesocket(ret); return(0); } } diff --git a/openssl/apps/smime.c b/openssl/apps/smime.c index c583f8a0e..d1fe32d31 100644 --- a/openssl/apps/smime.c +++ b/openssl/apps/smime.c @@ -541,8 +541,8 @@ int MAIN(int argc, char **argv) { if (!cipher) { -#ifndef OPENSSL_NO_RC2 - cipher = EVP_rc2_40_cbc(); +#ifndef OPENSSL_NO_DES + cipher = EVP_des_ede3_cbc(); #else BIO_printf(bio_err, "No cipher selected\n"); goto end; diff --git a/openssl/crypto/asn1/a_strnid.c b/openssl/crypto/asn1/a_strnid.c index 2fc48c155..2afd5a413 100644 --- a/openssl/crypto/asn1/a_strnid.c +++ b/openssl/crypto/asn1/a_strnid.c @@ -74,7 +74,7 @@ static int sk_table_cmp(const ASN1_STRING_TABLE * const *a, * certain software (e.g. Netscape) has problems with them. */ -static unsigned long global_mask = 0xFFFFFFFFL; +static unsigned long global_mask = B_ASN1_UTF8STRING; void ASN1_STRING_set_default_mask(unsigned long mask) { diff --git a/openssl/crypto/bio/bss_dgram.c b/openssl/crypto/bio/bss_dgram.c index 54c012c47..d9967e727 100644 --- a/openssl/crypto/bio/bss_dgram.c +++ b/openssl/crypto/bio/bss_dgram.c @@ -1333,7 +1333,7 @@ static long dgram_sctp_ctrl(BIO *b, int cmd, long num, void *ptr) bio_dgram_sctp_data *data = NULL; socklen_t sockopt_len = 0; struct sctp_authkeyid authkeyid; - struct sctp_authkey *authkey; + struct sctp_authkey *authkey = NULL; data = (bio_dgram_sctp_data *)b->ptr; @@ -1388,6 +1388,11 @@ static long dgram_sctp_ctrl(BIO *b, int cmd, long num, void *ptr) /* Add new key */ sockopt_len = sizeof(struct sctp_authkey) + 64 * sizeof(uint8_t); authkey = OPENSSL_malloc(sockopt_len); + if (authkey == NULL) + { + ret = -1; + break; + } memset(authkey, 0x00, sockopt_len); authkey->sca_keynumber = authkeyid.scact_keynumber + 1; #ifndef __FreeBSD__ @@ -1399,6 +1404,8 @@ static long dgram_sctp_ctrl(BIO *b, int cmd, long num, void *ptr) memcpy(&authkey->sca_key[0], ptr, 64 * sizeof(uint8_t)); ret = setsockopt(b->num, IPPROTO_SCTP, SCTP_AUTH_KEY, authkey, sockopt_len); + OPENSSL_free(authkey); + authkey = NULL; if (ret < 0) break; /* Reset active key */ diff --git a/openssl/crypto/bn/bn_mont.c b/openssl/crypto/bn/bn_mont.c index 427b5cf4d..ee8532c7d 100644 --- a/openssl/crypto/bn/bn_mont.c +++ b/openssl/crypto/bn/bn_mont.c @@ -478,32 +478,38 @@ BN_MONT_CTX *BN_MONT_CTX_copy(BN_MONT_CTX *to, BN_MONT_CTX *from) BN_MONT_CTX *BN_MONT_CTX_set_locked(BN_MONT_CTX **pmont, int lock, const BIGNUM *mod, BN_CTX *ctx) { - int got_write_lock = 0; BN_MONT_CTX *ret; CRYPTO_r_lock(lock); - if (!*pmont) + ret = *pmont; + CRYPTO_r_unlock(lock); + if (ret) + return ret; + + /* We don't want to serialise globally while doing our lazy-init math in + * BN_MONT_CTX_set. That punishes threads that are doing independent + * things. Instead, punish the case where more than one thread tries to + * lazy-init the same 'pmont', by having each do the lazy-init math work + * independently and only use the one from the thread that wins the race + * (the losers throw away the work they've done). */ + ret = BN_MONT_CTX_new(); + if (!ret) + return NULL; + if (!BN_MONT_CTX_set(ret, mod, ctx)) { - CRYPTO_r_unlock(lock); - CRYPTO_w_lock(lock); - got_write_lock = 1; + BN_MONT_CTX_free(ret); + return NULL; + } - if (!*pmont) - { - ret = BN_MONT_CTX_new(); - if (ret && !BN_MONT_CTX_set(ret, mod, ctx)) - BN_MONT_CTX_free(ret); - else - *pmont = ret; - } + /* The locked compare-and-set, after the local work is done. */ + CRYPTO_w_lock(lock); + if (*pmont) + { + BN_MONT_CTX_free(ret); + ret = *pmont; } - - ret = *pmont; - - if (got_write_lock) - CRYPTO_w_unlock(lock); else - CRYPTO_r_unlock(lock); - + *pmont = ret; + CRYPTO_w_unlock(lock); return ret; } diff --git a/openssl/crypto/cms/cms_env.c b/openssl/crypto/cms/cms_env.c index be20b1c02..add00bf99 100644 --- a/openssl/crypto/cms/cms_env.c +++ b/openssl/crypto/cms/cms_env.c @@ -185,6 +185,8 @@ CMS_RecipientInfo *CMS_add1_recipient_cert(CMS_ContentInfo *cms, if (flags & CMS_USE_KEYID) { ktri->version = 2; + if (env->version < 2) + env->version = 2; type = CMS_RECIPINFO_KEYIDENTIFIER; } else diff --git a/openssl/crypto/cms/cms_sd.c b/openssl/crypto/cms/cms_sd.c index 77fbd1359..51dd33a1c 100644 --- a/openssl/crypto/cms/cms_sd.c +++ b/openssl/crypto/cms/cms_sd.c @@ -158,8 +158,8 @@ static void cms_sd_set_version(CMS_SignedData *sd) if (sd->version < 3) sd->version = 3; } - else - sd->version = 1; + else if (si->version < 1) + si->version = 1; } if (sd->version < 1) diff --git a/openssl/crypto/cms/cms_smime.c b/openssl/crypto/cms/cms_smime.c index 8c56e3a85..1af9f3a60 100644 --- a/openssl/crypto/cms/cms_smime.c +++ b/openssl/crypto/cms/cms_smime.c @@ -611,7 +611,7 @@ int CMS_decrypt_set1_pkey(CMS_ContentInfo *cms, EVP_PKEY *pk, X509 *cert) STACK_OF(CMS_RecipientInfo) *ris; CMS_RecipientInfo *ri; int i, r; - int debug = 0; + int debug = 0, ri_match = 0; ris = CMS_get0_RecipientInfos(cms); if (ris) debug = cms->d.envelopedData->encryptedContentInfo->debug; @@ -620,6 +620,7 @@ int CMS_decrypt_set1_pkey(CMS_ContentInfo *cms, EVP_PKEY *pk, X509 *cert) ri = sk_CMS_RecipientInfo_value(ris, i); if (CMS_RecipientInfo_type(ri) != CMS_RECIPINFO_TRANS) continue; + ri_match = 1; /* If we have a cert try matching RecipientInfo * otherwise try them all. */ @@ -655,7 +656,7 @@ int CMS_decrypt_set1_pkey(CMS_ContentInfo *cms, EVP_PKEY *pk, X509 *cert) } } /* If no cert and not debugging always return success */ - if (!cert && !debug) + if (ri_match && !cert && !debug) { ERR_clear_error(); return 1; diff --git a/openssl/crypto/dso/dso_dlfcn.c b/openssl/crypto/dso/dso_dlfcn.c index 5f2254806..4a56aace0 100644 --- a/openssl/crypto/dso/dso_dlfcn.c +++ b/openssl/crypto/dso/dso_dlfcn.c @@ -464,7 +464,7 @@ static int dlfcn_pathbyaddr(void *addr,char *path,int sz) return len; } - ERR_add_error_data(4, "dlfcn_pathbyaddr(): ", dlerror()); + ERR_add_error_data(2, "dlfcn_pathbyaddr(): ", dlerror()); #endif return -1; } diff --git a/openssl/crypto/dso/dso_vms.c b/openssl/crypto/dso/dso_vms.c index eee20d14f..868513c39 100644 --- a/openssl/crypto/dso/dso_vms.c +++ b/openssl/crypto/dso/dso_vms.c @@ -61,7 +61,14 @@ #include <errno.h> #include "cryptlib.h" #include <openssl/dso.h> -#ifdef OPENSSL_SYS_VMS + +#ifndef OPENSSL_SYS_VMS +DSO_METHOD *DSO_METHOD_vms(void) + { + return NULL; + } +#else + #pragma message disable DOLLARID #include <rms.h> #include <lib$routines.h> @@ -69,7 +76,6 @@ #include <descrip.h> #include <starlet.h> #include "vms_rms.h" -#endif /* Some compiler options may mask the declaration of "_malloc32". */ #if __INITIAL_POINTER_SIZE && defined _ANSI_C_SOURCE @@ -82,12 +88,6 @@ #endif /* __INITIAL_POINTER_SIZE && defined _ANSI_C_SOURCE */ -#ifndef OPENSSL_SYS_VMS -DSO_METHOD *DSO_METHOD_vms(void) - { - return NULL; - } -#else #pragma message disable DOLLARID static int vms_load(DSO *dso); diff --git a/openssl/crypto/ec/ec_ameth.c b/openssl/crypto/ec/ec_ameth.c index 0ce452407..f715a238a 100644 --- a/openssl/crypto/ec/ec_ameth.c +++ b/openssl/crypto/ec/ec_ameth.c @@ -352,6 +352,7 @@ static int eckey_priv_encode(PKCS8_PRIV_KEY_INFO *p8, const EVP_PKEY *pkey) EC_KEY_set_enc_flags(ec_key, old_flags); OPENSSL_free(ep); ECerr(EC_F_ECKEY_PRIV_ENCODE, ERR_R_EC_LIB); + return 0; } /* restore old encoding flags */ EC_KEY_set_enc_flags(ec_key, old_flags); diff --git a/openssl/crypto/ec/ec_asn1.c b/openssl/crypto/ec/ec_asn1.c index 145807b61..e94f34e11 100644 --- a/openssl/crypto/ec/ec_asn1.c +++ b/openssl/crypto/ec/ec_asn1.c @@ -1435,8 +1435,11 @@ int i2o_ECPublicKey(EC_KEY *a, unsigned char **out) *out, buf_len, NULL)) { ECerr(EC_F_I2O_ECPUBLICKEY, ERR_R_EC_LIB); - OPENSSL_free(*out); - *out = NULL; + if (new_buffer) + { + OPENSSL_free(*out); + *out = NULL; + } return 0; } if (!new_buffer) diff --git a/openssl/crypto/ec/ec_lcl.h b/openssl/crypto/ec/ec_lcl.h index da7967df3..b0d48b6b5 100644 --- a/openssl/crypto/ec/ec_lcl.h +++ b/openssl/crypto/ec/ec_lcl.h @@ -404,7 +404,7 @@ int ec_GF2m_simple_mul(const EC_GROUP *group, EC_POINT *r, const BIGNUM *scalar, int ec_GF2m_precompute_mult(EC_GROUP *group, BN_CTX *ctx); int ec_GF2m_have_precompute_mult(const EC_GROUP *group); -#ifndef OPENSSL_EC_NISTP_64_GCC_128 +#ifndef OPENSSL_NO_EC_NISTP_64_GCC_128 /* method functions in ecp_nistp224.c */ int ec_GFp_nistp224_group_init(EC_GROUP *group); int ec_GFp_nistp224_group_set_curve(EC_GROUP *group, const BIGNUM *p, const BIGNUM *a, const BIGNUM *n, BN_CTX *); diff --git a/openssl/crypto/evp/bio_b64.c b/openssl/crypto/evp/bio_b64.c index ac6d441aa..16863fe23 100644 --- a/openssl/crypto/evp/bio_b64.c +++ b/openssl/crypto/evp/bio_b64.c @@ -226,6 +226,7 @@ static int b64_read(BIO *b, char *out, int outl) else if (ctx->start) { q=p=(unsigned char *)ctx->tmp; + num = 0; for (j=0; j<i; j++) { if (*(q++) != '\n') continue; diff --git a/openssl/crypto/evp/encode.c b/openssl/crypto/evp/encode.c index 28546a84b..4654bdc61 100644 --- a/openssl/crypto/evp/encode.c +++ b/openssl/crypto/evp/encode.c @@ -324,6 +324,7 @@ int EVP_DecodeUpdate(EVP_ENCODE_CTX *ctx, unsigned char *out, int *outl, v=EVP_DecodeBlock(out,d,n); n=0; if (v < 0) { rv=0; goto end; } + if (eof > v) { rv=-1; goto end; } ret+=(v-eof); } else diff --git a/openssl/crypto/opensslv.h b/openssl/crypto/opensslv.h index ebe718072..c3b6acec7 100644 --- a/openssl/crypto/opensslv.h +++ b/openssl/crypto/opensslv.h @@ -25,11 +25,11 @@ * (Prior to 0.9.5a beta1, a different scheme was used: MMNNFFRBB for * major minor fix final patch/beta) */ -#define OPENSSL_VERSION_NUMBER 0x1000107fL +#define OPENSSL_VERSION_NUMBER 0x1000108fL #ifdef OPENSSL_FIPS -#define OPENSSL_VERSION_TEXT "OpenSSL 1.0.1g-fips 7 Apr 2014" +#define OPENSSL_VERSION_TEXT "OpenSSL 1.0.1h-fips 5 Jun 2014" #else -#define OPENSSL_VERSION_TEXT "OpenSSL 1.0.1g 7 Apr 2014" +#define OPENSSL_VERSION_TEXT "OpenSSL 1.0.1h 5 Jun 2014" #endif #define OPENSSL_VERSION_PTEXT " part of " OPENSSL_VERSION_TEXT diff --git a/openssl/crypto/pkcs12/p12_crt.c b/openssl/crypto/pkcs12/p12_crt.c index a34915d02..35e8a4a8d 100644 --- a/openssl/crypto/pkcs12/p12_crt.c +++ b/openssl/crypto/pkcs12/p12_crt.c @@ -96,7 +96,11 @@ PKCS12 *PKCS12_create(char *pass, char *name, EVP_PKEY *pkey, X509 *cert, nid_cert = NID_pbe_WithSHA1And3_Key_TripleDES_CBC; else #endif +#ifdef OPENSSL_NO_RC2 + nid_cert = NID_pbe_WithSHA1And3_Key_TripleDES_CBC; +#else nid_cert = NID_pbe_WithSHA1And40BitRC2_CBC; +#endif } if (!nid_key) nid_key = NID_pbe_WithSHA1And3_Key_TripleDES_CBC; @@ -286,7 +290,11 @@ int PKCS12_add_safe(STACK_OF(PKCS7) **psafes, STACK_OF(PKCS12_SAFEBAG) *bags, free_safes = 0; if (nid_safe == 0) +#ifdef OPENSSL_NO_RC2 + nid_safe = NID_pbe_WithSHA1And3_Key_TripleDES_CBC; +#else nid_safe = NID_pbe_WithSHA1And40BitRC2_CBC; +#endif if (nid_safe == -1) p7 = PKCS12_pack_p7data(bags); diff --git a/openssl/crypto/pkcs12/p12_kiss.c b/openssl/crypto/pkcs12/p12_kiss.c index 206b1b0b1..c9b7ab61d 100644 --- a/openssl/crypto/pkcs12/p12_kiss.c +++ b/openssl/crypto/pkcs12/p12_kiss.c @@ -269,7 +269,7 @@ static int parse_bag(PKCS12_SAFEBAG *bag, const char *pass, int passlen, int len, r; unsigned char *data; len = ASN1_STRING_to_UTF8(&data, fname); - if(len > 0) { + if(len >= 0) { r = X509_alias_set1(x509, data, len); OPENSSL_free(data); if (!r) diff --git a/openssl/crypto/pkcs7/pk7_doit.c b/openssl/crypto/pkcs7/pk7_doit.c index 77fda3b82..d91aa116a 100644 --- a/openssl/crypto/pkcs7/pk7_doit.c +++ b/openssl/crypto/pkcs7/pk7_doit.c @@ -440,6 +440,11 @@ BIO *PKCS7_dataDecode(PKCS7 *p7, EVP_PKEY *pkey, BIO *in_bio, X509 *pcert) { case NID_pkcs7_signed: data_body=PKCS7_get_octet_string(p7->d.sign->contents); + if (!PKCS7_is_detached(p7) && data_body == NULL) + { + PKCS7err(PKCS7_F_PKCS7_DATADECODE,PKCS7_R_INVALID_SIGNED_DATA_TYPE); + goto err; + } md_sk=p7->d.sign->md_algs; break; case NID_pkcs7_signedAndEnveloped: @@ -928,6 +933,7 @@ int PKCS7_SIGNER_INFO_sign(PKCS7_SIGNER_INFO *si) if (EVP_DigestSignUpdate(&mctx,abuf,alen) <= 0) goto err; OPENSSL_free(abuf); + abuf = NULL; if (EVP_DigestSignFinal(&mctx, NULL, &siglen) <= 0) goto err; abuf = OPENSSL_malloc(siglen); diff --git a/openssl/crypto/pkcs7/pkcs7.h b/openssl/crypto/pkcs7/pkcs7.h index e4d443193..04f60379f 100644 --- a/openssl/crypto/pkcs7/pkcs7.h +++ b/openssl/crypto/pkcs7/pkcs7.h @@ -453,6 +453,7 @@ void ERR_load_PKCS7_strings(void); #define PKCS7_R_ERROR_SETTING_CIPHER 121 #define PKCS7_R_INVALID_MIME_TYPE 131 #define PKCS7_R_INVALID_NULL_POINTER 143 +#define PKCS7_R_INVALID_SIGNED_DATA_TYPE 155 #define PKCS7_R_MIME_NO_CONTENT_TYPE 132 #define PKCS7_R_MIME_PARSE_ERROR 133 #define PKCS7_R_MIME_SIG_PARSE_ERROR 134 diff --git a/openssl/crypto/pkcs7/pkcs7err.c b/openssl/crypto/pkcs7/pkcs7err.c index d0af32a26..f3db08e00 100644 --- a/openssl/crypto/pkcs7/pkcs7err.c +++ b/openssl/crypto/pkcs7/pkcs7err.c @@ -1,6 +1,6 @@ /* crypto/pkcs7/pkcs7err.c */ /* ==================================================================== - * Copyright (c) 1999-2007 The OpenSSL Project. All rights reserved. + * Copyright (c) 1999-2014 The OpenSSL Project. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -130,6 +130,7 @@ static ERR_STRING_DATA PKCS7_str_reasons[]= {ERR_REASON(PKCS7_R_ERROR_SETTING_CIPHER),"error setting cipher"}, {ERR_REASON(PKCS7_R_INVALID_MIME_TYPE) ,"invalid mime type"}, {ERR_REASON(PKCS7_R_INVALID_NULL_POINTER),"invalid null pointer"}, +{ERR_REASON(PKCS7_R_INVALID_SIGNED_DATA_TYPE),"invalid signed data type"}, {ERR_REASON(PKCS7_R_MIME_NO_CONTENT_TYPE),"mime no content type"}, {ERR_REASON(PKCS7_R_MIME_PARSE_ERROR) ,"mime parse error"}, {ERR_REASON(PKCS7_R_MIME_SIG_PARSE_ERROR),"mime sig parse error"}, diff --git a/openssl/crypto/rsa/rsa_ameth.c b/openssl/crypto/rsa/rsa_ameth.c index 5a2062f90..4c8ecd923 100644 --- a/openssl/crypto/rsa/rsa_ameth.c +++ b/openssl/crypto/rsa/rsa_ameth.c @@ -358,7 +358,7 @@ static int rsa_pss_param_print(BIO *bp, RSA_PSS_PARAMS *pss, if (i2a_ASN1_INTEGER(bp, pss->saltLength) <= 0) goto err; } - else if (BIO_puts(bp, "0x14 (default)") <= 0) + else if (BIO_puts(bp, "14 (default)") <= 0) goto err; BIO_puts(bp, "\n"); diff --git a/openssl/crypto/srp/srp_vfy.c b/openssl/crypto/srp/srp_vfy.c index 4a3d13edf..fdca19ff7 100644 --- a/openssl/crypto/srp/srp_vfy.c +++ b/openssl/crypto/srp/srp_vfy.c @@ -93,6 +93,9 @@ static int t_fromb64(unsigned char *a, const char *src) else a[i] = loc - b64table; ++i; } + /* if nothing valid to process we have a zero length response */ + if (i == 0) + return 0; size = i; i = size - 1; j = size; diff --git a/openssl/crypto/ts/ts_rsp_verify.c b/openssl/crypto/ts/ts_rsp_verify.c index afe16afbe..b7d170afa 100644 --- a/openssl/crypto/ts/ts_rsp_verify.c +++ b/openssl/crypto/ts/ts_rsp_verify.c @@ -629,6 +629,7 @@ static int TS_compute_imprint(BIO *data, TS_TST_INFO *tst_info, X509_ALGOR_free(*md_alg); OPENSSL_free(*imprint); *imprint_len = 0; + *imprint = NULL; return 0; } diff --git a/openssl/crypto/x509v3/v3_purp.c b/openssl/crypto/x509v3/v3_purp.c index ad688657e..f59bfc184 100644 --- a/openssl/crypto/x509v3/v3_purp.c +++ b/openssl/crypto/x509v3/v3_purp.c @@ -389,8 +389,8 @@ static void x509v3_cache_extensions(X509 *x) /* Handle proxy certificates */ if((pci=X509_get_ext_d2i(x, NID_proxyCertInfo, NULL, NULL))) { if (x->ex_flags & EXFLAG_CA - || X509_get_ext_by_NID(x, NID_subject_alt_name, 0) >= 0 - || X509_get_ext_by_NID(x, NID_issuer_alt_name, 0) >= 0) { + || X509_get_ext_by_NID(x, NID_subject_alt_name, -1) >= 0 + || X509_get_ext_by_NID(x, NID_issuer_alt_name, -1) >= 0) { x->ex_flags |= EXFLAG_INVALID; } if (pci->pcPathLengthConstraint) { @@ -670,7 +670,7 @@ static int check_purpose_timestamp_sign(const X509_PURPOSE *xp, const X509 *x, return 0; /* Extended Key Usage MUST be critical */ - i_ext = X509_get_ext_by_NID((X509 *) x, NID_ext_key_usage, 0); + i_ext = X509_get_ext_by_NID((X509 *) x, NID_ext_key_usage, -1); if (i_ext >= 0) { X509_EXTENSION *ext = X509_get_ext((X509 *) x, i_ext); diff --git a/openssl/doc/apps/cms.pod b/openssl/doc/apps/cms.pod index a09588a18..a76b3e0fd 100644 --- a/openssl/doc/apps/cms.pod +++ b/openssl/doc/apps/cms.pod @@ -90,6 +90,11 @@ decrypt mail using the supplied certificate and private key. Expects an encrypted mail message in MIME format for the input file. The decrypted mail is written to the output file. +=item B<-debug_decrypt> + +this option sets the B<CMS_DEBUG_DECRYPT> flag. This option should be used +with caution: see the notes section below. + =item B<-sign> sign mail using the supplied certificate and private key. Input file is @@ -446,32 +451,42 @@ Streaming is always used for the B<-sign> operation with detached data but since the content is no longer part of the CMS structure the encoding remains DER. +If the B<-decrypt> option is used without a recipient certificate then an +attempt is made to locate the recipient by trying each potential recipient +in turn using the supplied private key. To thwart the MMA attack +(Bleichenbacher's attack on PKCS #1 v1.5 RSA padding) all recipients are +tried whether they succeed or not and if no recipients match the message +is "decrypted" using a random key which will typically output garbage. +The B<-debug_decrypt> option can be used to disable the MMA attack protection +and return an error if no recipient can be found: this option should be used +with caution. For a fuller description see L<CMS_decrypt(3)|CMS_decrypt(3)>). + =head1 EXIT CODES =over 4 -=item 0 +=item Z<>0 the operation was completely successfully. -=item 1 +=item Z<>1 an error occurred parsing the command options. -=item 2 +=item Z<>2 one of the input files could not be read. -=item 3 +=item Z<>3 an error occurred creating the CMS file or when reading the MIME message. -=item 4 +=item Z<>4 an error occurred decrypting or verifying the message. -=item 5 +=item Z<>5 the message was verified correctly but an error occurred writing out the signers certificates. diff --git a/openssl/doc/apps/enc.pod b/openssl/doc/apps/enc.pod index 3dee4ed99..41791ad67 100644 --- a/openssl/doc/apps/enc.pod +++ b/openssl/doc/apps/enc.pod @@ -215,6 +215,10 @@ unsupported options (for example B<openssl enc -help>) includes a list of ciphers, supported by your versesion of OpenSSL, including ones provided by configured engines. +The B<enc> program does not support authenticated encryption modes +like CCM and GCM. The utility does not store or retrieve the +authentication tag. + base64 Base 64 diff --git a/openssl/doc/apps/s_server.pod b/openssl/doc/apps/s_server.pod index 6758ba308..f9b9ca532 100644 --- a/openssl/doc/apps/s_server.pod +++ b/openssl/doc/apps/s_server.pod @@ -44,6 +44,7 @@ B<openssl> B<s_server> [B<-no_ssl3>] [B<-no_tls1>] [B<-no_dhe>] +[B<-no_ecdhe>] [B<-bugs>] [B<-hack>] [B<-www>] @@ -131,6 +132,11 @@ a static set of parameters hard coded into the s_server program will be used. if this option is set then no DH parameters will be loaded effectively disabling the ephemeral DH cipher suites. +=item B<-no_ecdhe> + +if this option is set then no ECDH parameters will be loaded effectively +disabling the ephemeral ECDH cipher suites. + =item B<-no_tmp_rsa> certain export cipher suites sometimes use a temporary RSA key, this option diff --git a/openssl/doc/apps/smime.pod b/openssl/doc/apps/smime.pod index e4e89af84..d39a59a90 100644 --- a/openssl/doc/apps/smime.pod +++ b/openssl/doc/apps/smime.pod @@ -159,7 +159,7 @@ EVP_get_cipherbyname() function) can also be used preceded by a dash, for example B<-aes_128_cbc>. See L<B<enc>|enc(1)> for list of ciphers supported by your version of OpenSSL. -If not specified 40 bit RC2 is used. Only used with B<-encrypt>. +If not specified triple DES is used. Only used with B<-encrypt>. =item B<-nointern> @@ -308,28 +308,28 @@ remains DER. =over 4 -=item 0 +=item Z<>0 the operation was completely successfully. -=item 1 +=item Z<>1 an error occurred parsing the command options. -=item 2 +=item Z<>2 one of the input files could not be read. -=item 3 +=item Z<>3 an error occurred creating the PKCS#7 file or when reading the MIME message. -=item 4 +=item Z<>4 an error occurred decrypting or verifying the message. -=item 5 +=item Z<>5 the message was verified correctly but an error occurred writing out the signers certificates. diff --git a/openssl/doc/apps/verify.pod b/openssl/doc/apps/verify.pod index da683004b..f35d40295 100644 --- a/openssl/doc/apps/verify.pod +++ b/openssl/doc/apps/verify.pod @@ -25,6 +25,7 @@ B<openssl> B<verify> [B<-untrusted file>] [B<-help>] [B<-issuer_checks>] +[B<-attime timestamp>] [B<-verbose>] [B<->] [certificates] @@ -80,6 +81,12 @@ rejected. The presence of rejection messages does not itself imply that anything is wrong; during the normal verification process, several rejections may take place. +=item B<-attime timestamp> + +Perform validation checks using time specified by B<timestamp> and not +current system time. B<timestamp> is the number of seconds since +01.01.1970 (UNIX time). + =item B<-policy arg> Enable policy processing and add B<arg> to the user-initial-policy-set (see @@ -386,7 +393,7 @@ an application specific error. Unused. =head1 BUGS -Although the issuer checks are a considerably improvement over the old technique they still +Although the issuer checks are a considerable improvement over the old technique they still suffer from limitations in the underlying X509_LOOKUP API. One consequence of this is that trusted certificates with matching subject name must either appear in a file (as specified by the B<-CAfile> option) or a directory (as specified by B<-CApath>. If they occur in both then only diff --git a/openssl/doc/apps/version.pod b/openssl/doc/apps/version.pod index e00324c44..58f543bc3 100644 --- a/openssl/doc/apps/version.pod +++ b/openssl/doc/apps/version.pod @@ -13,6 +13,7 @@ B<openssl version> [B<-o>] [B<-f>] [B<-p>] +[B<-d>] =head1 DESCRIPTION @@ -38,7 +39,7 @@ the date the current version of OpenSSL was built. option information: various options set when the library was built. -=item B<-c> +=item B<-f> compilation flags. diff --git a/openssl/doc/apps/x509v3_config.pod b/openssl/doc/apps/x509v3_config.pod index 0450067cf..13ff85b17 100644 --- a/openssl/doc/apps/x509v3_config.pod +++ b/openssl/doc/apps/x509v3_config.pod @@ -301,7 +301,7 @@ Example: O=Organisation CN=Some Name - + =head2 Certificate Policies. This is a I<raw> extension. All the fields of this extension can be set by @@ -390,7 +390,7 @@ Examples: nameConstraints=permitted;email:.somedomain.com nameConstraints=excluded;email:.com -issuingDistributionPoint = idp_section + =head2 OCSP No Check diff --git a/openssl/doc/crypto/CMS_decrypt.pod b/openssl/doc/crypto/CMS_decrypt.pod index d857e4f93..3fa9212af 100644 --- a/openssl/doc/crypto/CMS_decrypt.pod +++ b/openssl/doc/crypto/CMS_decrypt.pod @@ -27,7 +27,21 @@ function or errors about unknown algorithms will occur. Although the recipients certificate is not needed to decrypt the data it is needed to locate the appropriate (of possible several) recipients in the CMS -structure. If B<cert> is set to NULL all possible recipients are tried. +structure. + +If B<cert> is set to NULL all possible recipients are tried. This case however +is problematic. To thwart the MMA attack (Bleichenbacher's attack on +PKCS #1 v1.5 RSA padding) all recipients are tried whether they succeed or +not. If no recipient succeeds then a random symmetric key is used to decrypt +the content: this will typically output garbage and may (but is not guaranteed +to) ultimately return a padding error only. If CMS_decrypt() just returned an +error when all recipient encrypted keys failed to decrypt an attacker could +use this in a timing attack. If the special flag B<CMS_DEBUG_DECRYPT> is set +then the above behaviour is modified and an error B<is> returned if no +recipient encrypted key can be decrypted B<without> generating a random +content encryption key. Applications should use this flag with +B<extreme caution> especially in automated gateways as it can leave them +open to attack. It is possible to determine the correct recipient key by other means (for example looking them up in a database) and setting them in the CMS structure diff --git a/openssl/doc/crypto/CONF_modules_free.pod b/openssl/doc/crypto/CONF_modules_free.pod index 87bc7b783..347020c5f 100644 --- a/openssl/doc/crypto/CONF_modules_free.pod +++ b/openssl/doc/crypto/CONF_modules_free.pod @@ -37,7 +37,7 @@ None of the functions return a value. =head1 SEE ALSO L<conf(5)|conf(5)>, L<OPENSSL_config(3)|OPENSSL_config(3)>, -L<CONF_modules_load_file(3), CONF_modules_load_file(3)> +L<CONF_modules_load_file(3)|CONF_modules_load_file(3)> =head1 HISTORY diff --git a/openssl/doc/crypto/CONF_modules_load_file.pod b/openssl/doc/crypto/CONF_modules_load_file.pod index 9965d69bf..0c4d92685 100644 --- a/openssl/doc/crypto/CONF_modules_load_file.pod +++ b/openssl/doc/crypto/CONF_modules_load_file.pod @@ -51,7 +51,7 @@ return value of the failing module (this will always be zero or negative). =head1 SEE ALSO L<conf(5)|conf(5)>, L<OPENSSL_config(3)|OPENSSL_config(3)>, -L<CONF_free(3), CONF_free(3)>, L<err(3),err(3)> +L<CONF_free(3)|CONF_free(3)>, L<err(3)|err(3)> =head1 HISTORY diff --git a/openssl/doc/crypto/OPENSSL_config.pod b/openssl/doc/crypto/OPENSSL_config.pod index e7bba2aac..888de88f6 100644 --- a/openssl/doc/crypto/OPENSSL_config.pod +++ b/openssl/doc/crypto/OPENSSL_config.pod @@ -73,7 +73,7 @@ Neither OPENSSL_config() nor OPENSSL_no_config() return a value. =head1 SEE ALSO L<conf(5)|conf(5)>, L<CONF_load_modules_file(3)|CONF_load_modules_file(3)>, -L<CONF_modules_free(3),CONF_modules_free(3)> +L<CONF_modules_free(3)|CONF_modules_free(3)> =head1 HISTORY diff --git a/openssl/doc/crypto/X509_NAME_ENTRY_get_object.pod b/openssl/doc/crypto/X509_NAME_ENTRY_get_object.pod index 41902c0d4..4716e7ee7 100644 --- a/openssl/doc/crypto/X509_NAME_ENTRY_get_object.pod +++ b/openssl/doc/crypto/X509_NAME_ENTRY_get_object.pod @@ -65,7 +65,7 @@ set first so the relevant field information can be looked up internally. =head1 SEE ALSO L<ERR_get_error(3)|ERR_get_error(3)>, L<d2i_X509_NAME(3)|d2i_X509_NAME(3)>, -L<OBJ_nid2obj(3),OBJ_nid2obj(3)> +L<OBJ_nid2obj(3)|OBJ_nid2obj(3)> =head1 HISTORY diff --git a/openssl/doc/crypto/X509_STORE_CTX_get_ex_new_index.pod b/openssl/doc/crypto/X509_STORE_CTX_get_ex_new_index.pod index 8d6b9dda4..8a9243d75 100644 --- a/openssl/doc/crypto/X509_STORE_CTX_get_ex_new_index.pod +++ b/openssl/doc/crypto/X509_STORE_CTX_get_ex_new_index.pod @@ -15,7 +15,7 @@ X509_STORE_CTX_get_ex_new_index, X509_STORE_CTX_set_ex_data, X509_STORE_CTX_get_ int X509_STORE_CTX_set_ex_data(X509_STORE_CTX *d, int idx, void *arg); - char *X509_STORE_CTX_get_ex_data(X509_STORE_CTX *d, int idx); + void *X509_STORE_CTX_get_ex_data(X509_STORE_CTX *d, int idx); =head1 DESCRIPTION diff --git a/openssl/doc/fingerprints.txt b/openssl/doc/fingerprints.txt index 7d05a8559..4030c81fa 100644 --- a/openssl/doc/fingerprints.txt +++ b/openssl/doc/fingerprints.txt @@ -21,6 +21,13 @@ pub 2048R/F295C759 1998-12-13 Key fingerprint = D0 5D 8C 61 6E 27 E6 60 41 EC B1 B8 D5 7E E5 97 uid Dr S N Henson <shenson@drh-consultancy.demon.co.uk> +pub 4096R/FA40E9E2 2005-03-19 + Key fingerprint = 6260 5AA4 334A F9F0 DDE5 D349 D357 7507 FA40 E9E2 +uid Dr Stephen Henson <shenson@opensslfoundation.com> +uid Dr Stephen Henson <shenson@drh-consultancy.co.uk> +uid Dr Stephen N Henson <steve@openssl.org> +sub 4096R/8811F530 2005-03-19 + pub 1024R/49A563D9 1997-02-24 Key fingerprint = 7B 79 19 FA 71 6B 87 25 0E 77 21 E5 52 D9 83 BF uid Mark Cox <mjc@redhat.com> diff --git a/openssl/doc/ssl/SSL_COMP_add_compression_method.pod b/openssl/doc/ssl/SSL_COMP_add_compression_method.pod index 42fa66b19..f4d191c9b 100644 --- a/openssl/doc/ssl/SSL_COMP_add_compression_method.pod +++ b/openssl/doc/ssl/SSL_COMP_add_compression_method.pod @@ -53,11 +53,11 @@ SSL_COMP_add_compression_method() may return the following values: =over 4 -=item 0 +=item Z<>0 The operation succeeded. -=item 1 +=item Z<>1 The operation failed. Check the error queue to find out the reason. diff --git a/openssl/doc/ssl/SSL_CTX_add_session.pod b/openssl/doc/ssl/SSL_CTX_add_session.pod index 82676b26b..8e0abd36c 100644 --- a/openssl/doc/ssl/SSL_CTX_add_session.pod +++ b/openssl/doc/ssl/SSL_CTX_add_session.pod @@ -52,13 +52,13 @@ The following values are returned by all functions: =over 4 -=item 0 +=item Z<>0 The operation failed. In case of the add operation, it was tried to add the same (identical) session twice. In case of the remove operation, the session was not found in the cache. -=item 1 +=item Z<>1 The operation succeeded. diff --git a/openssl/doc/ssl/SSL_CTX_load_verify_locations.pod b/openssl/doc/ssl/SSL_CTX_load_verify_locations.pod index 84a799fc7..d1d897719 100644 --- a/openssl/doc/ssl/SSL_CTX_load_verify_locations.pod +++ b/openssl/doc/ssl/SSL_CTX_load_verify_locations.pod @@ -100,13 +100,13 @@ The following return values can occur: =over 4 -=item 0 +=item Z<>0 The operation failed because B<CAfile> and B<CApath> are NULL or the processing at one of the locations specified failed. Check the error stack to find out the reason. -=item 1 +=item Z<>1 The operation succeeded. diff --git a/openssl/doc/ssl/SSL_CTX_set_client_CA_list.pod b/openssl/doc/ssl/SSL_CTX_set_client_CA_list.pod index 5e6613335..5e9739266 100644 --- a/openssl/doc/ssl/SSL_CTX_set_client_CA_list.pod +++ b/openssl/doc/ssl/SSL_CTX_set_client_CA_list.pod @@ -66,13 +66,13 @@ values: =over 4 -=item 0 +=item Z<>0 A failure while manipulating the STACK_OF(X509_NAME) object occurred or the X509_NAME could not be extracted from B<cacert>. Check the error stack to find out the reason. -=item 1 +=item Z<>1 The operation succeeded. diff --git a/openssl/doc/ssl/SSL_CTX_set_msg_callback.pod b/openssl/doc/ssl/SSL_CTX_set_msg_callback.pod index 0015e6ea7..8b82d94a3 100644 --- a/openssl/doc/ssl/SSL_CTX_set_msg_callback.pod +++ b/openssl/doc/ssl/SSL_CTX_set_msg_callback.pod @@ -11,8 +11,8 @@ SSL_CTX_set_msg_callback, SSL_CTX_set_msg_callback_arg, SSL_set_msg_callback, SS void SSL_CTX_set_msg_callback(SSL_CTX *ctx, void (*cb)(int write_p, int version, int content_type, const void *buf, size_t len, SSL *ssl, void *arg)); void SSL_CTX_set_msg_callback_arg(SSL_CTX *ctx, void *arg); - void SSL_set_msg_callback(SSL_CTX *ctx, void (*cb)(int write_p, int version, int content_type, const void *buf, size_t len, SSL *ssl, void *arg)); - void SSL_set_msg_callback_arg(SSL_CTX *ctx, void *arg); + void SSL_set_msg_callback(SSL *ssl, void (*cb)(int write_p, int version, int content_type, const void *buf, size_t len, SSL *ssl, void *arg)); + void SSL_set_msg_callback_arg(SSL *ssl, void *arg); =head1 DESCRIPTION diff --git a/openssl/doc/ssl/SSL_CTX_set_options.pod b/openssl/doc/ssl/SSL_CTX_set_options.pod index fded0601b..d8866927a 100644 --- a/openssl/doc/ssl/SSL_CTX_set_options.pod +++ b/openssl/doc/ssl/SSL_CTX_set_options.pod @@ -112,6 +112,12 @@ vulnerability affecting CBC ciphers, which cannot be handled by some broken SSL implementations. This option has no effect for connections using other ciphers. +=item SSL_OP_TLSEXT_PADDING + +Adds a padding extension to ensure the ClientHello size is never between +256 and 511 bytes in length. This is needed as a workaround for some +implementations. + =item SSL_OP_ALL All of the above bug workarounds. diff --git a/openssl/doc/ssl/SSL_CTX_set_session_id_context.pod b/openssl/doc/ssl/SSL_CTX_set_session_id_context.pod index 58fc68550..7c9e51533 100644 --- a/openssl/doc/ssl/SSL_CTX_set_session_id_context.pod +++ b/openssl/doc/ssl/SSL_CTX_set_session_id_context.pod @@ -64,13 +64,13 @@ return the following values: =over 4 -=item 0 +=item Z<>0 The length B<sid_ctx_len> of the session id context B<sid_ctx> exceeded the maximum allowed length of B<SSL_MAX_SSL_SESSION_ID_LENGTH>. The error is logged to the error stack. -=item 1 +=item Z<>1 The operation succeeded. diff --git a/openssl/doc/ssl/SSL_CTX_set_ssl_version.pod b/openssl/doc/ssl/SSL_CTX_set_ssl_version.pod index 254f2b439..e254f9657 100644 --- a/openssl/doc/ssl/SSL_CTX_set_ssl_version.pod +++ b/openssl/doc/ssl/SSL_CTX_set_ssl_version.pod @@ -42,11 +42,11 @@ and SSL_set_ssl_method(): =over 4 -=item 0 +=item Z<>0 The new choice failed, check the error stack to find out the reason. -=item 1 +=item Z<>1 The operation succeeded. diff --git a/openssl/doc/ssl/SSL_CTX_use_psk_identity_hint.pod b/openssl/doc/ssl/SSL_CTX_use_psk_identity_hint.pod index 7e60df5ba..9da7201a9 100644 --- a/openssl/doc/ssl/SSL_CTX_use_psk_identity_hint.pod +++ b/openssl/doc/ssl/SSL_CTX_use_psk_identity_hint.pod @@ -96,7 +96,7 @@ data to B<psk> and return the length of the random data, so the connection will fail with decryption_error before it will be finished completely. -=item 0 +=item Z<>0 PSK identity was not found. An "unknown_psk_identity" alert message will be sent and the connection setup fails. diff --git a/openssl/doc/ssl/SSL_accept.pod b/openssl/doc/ssl/SSL_accept.pod index b1c34d15b..223944417 100644 --- a/openssl/doc/ssl/SSL_accept.pod +++ b/openssl/doc/ssl/SSL_accept.pod @@ -44,13 +44,13 @@ The following return values can occur: =over 4 -=item 0 +=item Z<>0 The TLS/SSL handshake was not successful but was shut down controlled and by the specifications of the TLS/SSL protocol. Call SSL_get_error() with the return value B<ret> to find out the reason. -=item 1 +=item Z<>1 The TLS/SSL handshake was successfully completed, a TLS/SSL connection has been established. diff --git a/openssl/doc/ssl/SSL_clear.pod b/openssl/doc/ssl/SSL_clear.pod index d4df1bfac..ba192bd51 100644 --- a/openssl/doc/ssl/SSL_clear.pod +++ b/openssl/doc/ssl/SSL_clear.pod @@ -56,12 +56,12 @@ The following return values can occur: =over 4 -=item 0 +=item Z<>0 The SSL_clear() operation could not be performed. Check the error stack to find out the reason. -=item 1 +=item Z<>1 The SSL_clear() operation was successful. diff --git a/openssl/doc/ssl/SSL_connect.pod b/openssl/doc/ssl/SSL_connect.pod index 946ca89d7..68e2b82b8 100644 --- a/openssl/doc/ssl/SSL_connect.pod +++ b/openssl/doc/ssl/SSL_connect.pod @@ -41,13 +41,13 @@ The following return values can occur: =over 4 -=item 0 +=item Z<>0 The TLS/SSL handshake was not successful but was shut down controlled and by the specifications of the TLS/SSL protocol. Call SSL_get_error() with the return value B<ret> to find out the reason. -=item 1 +=item Z<>1 The TLS/SSL handshake was successfully completed, a TLS/SSL connection has been established. diff --git a/openssl/doc/ssl/SSL_do_handshake.pod b/openssl/doc/ssl/SSL_do_handshake.pod index 7f8cf249e..b35ddf5f1 100644 --- a/openssl/doc/ssl/SSL_do_handshake.pod +++ b/openssl/doc/ssl/SSL_do_handshake.pod @@ -45,13 +45,13 @@ The following return values can occur: =over 4 -=item 0 +=item Z<>0 The TLS/SSL handshake was not successful but was shut down controlled and by the specifications of the TLS/SSL protocol. Call SSL_get_error() with the return value B<ret> to find out the reason. -=item 1 +=item Z<>1 The TLS/SSL handshake was successfully completed, a TLS/SSL connection has been established. diff --git a/openssl/doc/ssl/SSL_get_peer_cert_chain.pod b/openssl/doc/ssl/SSL_get_peer_cert_chain.pod index 49fb88f86..059376c76 100644 --- a/openssl/doc/ssl/SSL_get_peer_cert_chain.pod +++ b/openssl/doc/ssl/SSL_get_peer_cert_chain.pod @@ -8,11 +8,11 @@ SSL_get_peer_cert_chain - get the X509 certificate chain of the peer #include <openssl/ssl.h> - STACKOF(X509) *SSL_get_peer_cert_chain(const SSL *ssl); + STACK_OF(X509) *SSL_get_peer_cert_chain(const SSL *ssl); =head1 DESCRIPTION -SSL_get_peer_cert_chain() returns a pointer to STACKOF(X509) certificates +SSL_get_peer_cert_chain() returns a pointer to STACK_OF(X509) certificates forming the certificate chain of the peer. If called on the client side, the stack also contains the peer's certificate; if called on the server side, the peer's certificate must be obtained separately using @@ -24,7 +24,7 @@ If the peer did not present a certificate, NULL is returned. The peer certificate chain is not necessarily available after reusing a session, in which case a NULL pointer is returned. -The reference count of the STACKOF(X509) object is not incremented. +The reference count of the STACK_OF(X509) object is not incremented. If the corresponding session is freed, the pointer must not be used any longer. @@ -39,7 +39,7 @@ The following return values can occur: No certificate was presented by the peer or no connection was established or the certificate chain is no longer available when a session is reused. -=item Pointer to a STACKOF(X509) +=item Pointer to a STACK_OF(X509) The return value points to the certificate chain presented by the peer. diff --git a/openssl/doc/ssl/SSL_read.pod b/openssl/doc/ssl/SSL_read.pod index 7038cd2d7..8ca0ce505 100644 --- a/openssl/doc/ssl/SSL_read.pod +++ b/openssl/doc/ssl/SSL_read.pod @@ -86,7 +86,7 @@ The following return values can occur: The read operation was successful; the return value is the number of bytes actually read from the TLS/SSL connection. -=item 0 +=item Z<>0 The read operation was not successful. The reason may either be a clean shutdown due to a "close notify" alert sent by the peer (in which case diff --git a/openssl/doc/ssl/SSL_session_reused.pod b/openssl/doc/ssl/SSL_session_reused.pod index da7d06264..b09d8a71b 100644 --- a/openssl/doc/ssl/SSL_session_reused.pod +++ b/openssl/doc/ssl/SSL_session_reused.pod @@ -27,11 +27,11 @@ The following return values can occur: =over 4 -=item 0 +=item Z<>0 A new session was negotiated. -=item 1 +=item Z<>1 A session was reused. diff --git a/openssl/doc/ssl/SSL_set_fd.pod b/openssl/doc/ssl/SSL_set_fd.pod index 70291128f..148087160 100644 --- a/openssl/doc/ssl/SSL_set_fd.pod +++ b/openssl/doc/ssl/SSL_set_fd.pod @@ -35,11 +35,11 @@ The following return values can occur: =over 4 -=item 0 +=item Z<>0 The operation failed. Check the error stack to find out why. -=item 1 +=item Z<>1 The operation succeeded. diff --git a/openssl/doc/ssl/SSL_set_session.pod b/openssl/doc/ssl/SSL_set_session.pod index 5f54714ad..197b52183 100644 --- a/openssl/doc/ssl/SSL_set_session.pod +++ b/openssl/doc/ssl/SSL_set_session.pod @@ -37,11 +37,11 @@ The following return values can occur: =over 4 -=item 0 +=item Z<>0 The operation failed; check the error stack to find out the reason. -=item 1 +=item Z<>1 The operation succeeded. diff --git a/openssl/doc/ssl/SSL_shutdown.pod b/openssl/doc/ssl/SSL_shutdown.pod index 42a89b7c6..85d4a64b0 100644 --- a/openssl/doc/ssl/SSL_shutdown.pod +++ b/openssl/doc/ssl/SSL_shutdown.pod @@ -92,14 +92,14 @@ The following return values can occur: =over 4 -=item 0 +=item Z<>0 The shutdown is not yet finished. Call SSL_shutdown() for a second time, if a bidirectional shutdown shall be performed. The output of L<SSL_get_error(3)|SSL_get_error(3)> may be misleading, as an erroneous SSL_ERROR_SYSCALL may be flagged even though no error occurred. -=item 1 +=item Z<>1 The shutdown was successfully completed. The "close notify" alert was sent and the peer's "close notify" alert was received. diff --git a/openssl/doc/ssl/SSL_write.pod b/openssl/doc/ssl/SSL_write.pod index e013c12d5..a57617f3e 100644 --- a/openssl/doc/ssl/SSL_write.pod +++ b/openssl/doc/ssl/SSL_write.pod @@ -79,7 +79,7 @@ The following return values can occur: The write operation was successful, the return value is the number of bytes actually written to the TLS/SSL connection. -=item 0 +=item Z<>0 The write operation was not successful. Probably the underlying connection was closed. Call SSL_get_error() with the return value B<ret> to find out, diff --git a/openssl/engines/ccgost/gost_ameth.c b/openssl/engines/ccgost/gost_ameth.c index 2cde1fcfd..8b9230b9a 100644 --- a/openssl/engines/ccgost/gost_ameth.c +++ b/openssl/engines/ccgost/gost_ameth.c @@ -269,7 +269,7 @@ static int pkey_ctrl_gost(EVP_PKEY *pkey, int op, case ASN1_PKEY_CTRL_CMS_ENVELOPE: if (arg1 == 0) { - X509_ALGOR *alg; + X509_ALGOR *alg = NULL; ASN1_STRING * params = encode_gost_algor_params(pkey); if (!params) { diff --git a/openssl/include/openssl/aes.h b/openssl/include/openssl/aes.h index f555c13ed..f555c13ed 100644..120000 --- a/openssl/include/openssl/aes.h +++ b/openssl/include/openssl/aes.h diff --git a/openssl/include/openssl/asn1.h b/openssl/include/openssl/asn1.h index dd514954a..dd514954a 100644..120000 --- a/openssl/include/openssl/asn1.h +++ b/openssl/include/openssl/asn1.h diff --git a/openssl/include/openssl/asn1_mac.h b/openssl/include/openssl/asn1_mac.h index 97781d993..97781d993 100644..120000 --- a/openssl/include/openssl/asn1_mac.h +++ b/openssl/include/openssl/asn1_mac.h diff --git a/openssl/include/openssl/asn1t.h b/openssl/include/openssl/asn1t.h index 31c87c388..31c87c388 100644..120000 --- a/openssl/include/openssl/asn1t.h +++ b/openssl/include/openssl/asn1t.h diff --git a/openssl/include/openssl/bio.h b/openssl/include/openssl/bio.h index c598b6f73..c598b6f73 100644..120000 --- a/openssl/include/openssl/bio.h +++ b/openssl/include/openssl/bio.h diff --git a/openssl/include/openssl/blowfish.h b/openssl/include/openssl/blowfish.h index 88bf92234..88bf92234 100644..120000 --- a/openssl/include/openssl/blowfish.h +++ b/openssl/include/openssl/blowfish.h diff --git a/openssl/include/openssl/bn.h b/openssl/include/openssl/bn.h index 5c251c135..5c251c135 100644..120000 --- a/openssl/include/openssl/bn.h +++ b/openssl/include/openssl/bn.h diff --git a/openssl/include/openssl/buffer.h b/openssl/include/openssl/buffer.h index 76ea7114a..76ea7114a 100644..120000 --- a/openssl/include/openssl/buffer.h +++ b/openssl/include/openssl/buffer.h diff --git a/openssl/include/openssl/camellia.h b/openssl/include/openssl/camellia.h index ad10f9792..ad10f9792 100644..120000 --- a/openssl/include/openssl/camellia.h +++ b/openssl/include/openssl/camellia.h diff --git a/openssl/include/openssl/cast.h b/openssl/include/openssl/cast.h index b775ab04b..b775ab04b 100644..120000 --- a/openssl/include/openssl/cast.h +++ b/openssl/include/openssl/cast.h diff --git a/openssl/include/openssl/cmac.h b/openssl/include/openssl/cmac.h index bfb70c468..bfb70c468 100644..120000 --- a/openssl/include/openssl/cmac.h +++ b/openssl/include/openssl/cmac.h diff --git a/openssl/include/openssl/cms.h b/openssl/include/openssl/cms.h index 0f651adde..0f651adde 100644..120000 --- a/openssl/include/openssl/cms.h +++ b/openssl/include/openssl/cms.h diff --git a/openssl/include/openssl/comp.h b/openssl/include/openssl/comp.h index 712c9d4ae..712c9d4ae 100644..120000 --- a/openssl/include/openssl/comp.h +++ b/openssl/include/openssl/comp.h diff --git a/openssl/include/openssl/conf.h b/openssl/include/openssl/conf.h index 44156b189..44156b189 100644..120000 --- a/openssl/include/openssl/conf.h +++ b/openssl/include/openssl/conf.h diff --git a/openssl/include/openssl/conf_api.h b/openssl/include/openssl/conf_api.h index 26b42198a..26b42198a 100644..120000 --- a/openssl/include/openssl/conf_api.h +++ b/openssl/include/openssl/conf_api.h diff --git a/openssl/include/openssl/crypto.h b/openssl/include/openssl/crypto.h index 2f3f63cb0..2f3f63cb0 100644..120000 --- a/openssl/include/openssl/crypto.h +++ b/openssl/include/openssl/crypto.h diff --git a/openssl/include/openssl/des.h b/openssl/include/openssl/des.h index 5eb7c88b3..5eb7c88b3 100644..120000 --- a/openssl/include/openssl/des.h +++ b/openssl/include/openssl/des.h diff --git a/openssl/include/openssl/des_old.h b/openssl/include/openssl/des_old.h index 970989880..970989880 100644..120000 --- a/openssl/include/openssl/des_old.h +++ b/openssl/include/openssl/des_old.h diff --git a/openssl/include/openssl/dh.h b/openssl/include/openssl/dh.h index c0eacb5eb..c0eacb5eb 100644..120000 --- a/openssl/include/openssl/dh.h +++ b/openssl/include/openssl/dh.h diff --git a/openssl/include/openssl/dsa.h b/openssl/include/openssl/dsa.h index ad4695f9b..ad4695f9b 100644..120000 --- a/openssl/include/openssl/dsa.h +++ b/openssl/include/openssl/dsa.h diff --git a/openssl/include/openssl/dso.h b/openssl/include/openssl/dso.h index b1f215daf..b1f215daf 100644..120000 --- a/openssl/include/openssl/dso.h +++ b/openssl/include/openssl/dso.h diff --git a/openssl/include/openssl/dtls1.h b/openssl/include/openssl/dtls1.h index 95aef9913..95aef9913 100644..120000 --- a/openssl/include/openssl/dtls1.h +++ b/openssl/include/openssl/dtls1.h diff --git a/openssl/include/openssl/e_os2.h b/openssl/include/openssl/e_os2.h index 0e8c03992..0e8c03992 100644..120000 --- a/openssl/include/openssl/e_os2.h +++ b/openssl/include/openssl/e_os2.h diff --git a/openssl/include/openssl/ebcdic.h b/openssl/include/openssl/ebcdic.h index a7ee60e0a..a7ee60e0a 100644..120000 --- a/openssl/include/openssl/ebcdic.h +++ b/openssl/include/openssl/ebcdic.h diff --git a/openssl/include/openssl/ec.h b/openssl/include/openssl/ec.h index 245497eda..245497eda 100644..120000 --- a/openssl/include/openssl/ec.h +++ b/openssl/include/openssl/ec.h diff --git a/openssl/include/openssl/ecdh.h b/openssl/include/openssl/ecdh.h index 3fd1c3ba3..3fd1c3ba3 100644..120000 --- a/openssl/include/openssl/ecdh.h +++ b/openssl/include/openssl/ecdh.h diff --git a/openssl/include/openssl/ecdsa.h b/openssl/include/openssl/ecdsa.h index e48acc669..e48acc669 100644..120000 --- a/openssl/include/openssl/ecdsa.h +++ b/openssl/include/openssl/ecdsa.h diff --git a/openssl/include/openssl/engine.h b/openssl/include/openssl/engine.h index a02073e32..a02073e32 100644..120000 --- a/openssl/include/openssl/engine.h +++ b/openssl/include/openssl/engine.h diff --git a/openssl/include/openssl/err.h b/openssl/include/openssl/err.h index 20f65bd9c..20f65bd9c 100644..120000 --- a/openssl/include/openssl/err.h +++ b/openssl/include/openssl/err.h diff --git a/openssl/include/openssl/evp.h b/openssl/include/openssl/evp.h index 7e3a904ae..7e3a904ae 100644..120000 --- a/openssl/include/openssl/evp.h +++ b/openssl/include/openssl/evp.h diff --git a/openssl/include/openssl/hmac.h b/openssl/include/openssl/hmac.h index de19ba7ed..de19ba7ed 100644..120000 --- a/openssl/include/openssl/hmac.h +++ b/openssl/include/openssl/hmac.h diff --git a/openssl/include/openssl/idea.h b/openssl/include/openssl/idea.h index 724fa3458..724fa3458 100644..120000 --- a/openssl/include/openssl/idea.h +++ b/openssl/include/openssl/idea.h diff --git a/openssl/include/openssl/krb5_asn.h b/openssl/include/openssl/krb5_asn.h index 1172e522e..1172e522e 100644..120000 --- a/openssl/include/openssl/krb5_asn.h +++ b/openssl/include/openssl/krb5_asn.h diff --git a/openssl/include/openssl/kssl.h b/openssl/include/openssl/kssl.h index 2e5c2cd4d..2e5c2cd4d 100644..120000 --- a/openssl/include/openssl/kssl.h +++ b/openssl/include/openssl/kssl.h diff --git a/openssl/include/openssl/lhash.h b/openssl/include/openssl/lhash.h index 56eb09918..56eb09918 100644..120000 --- a/openssl/include/openssl/lhash.h +++ b/openssl/include/openssl/lhash.h diff --git a/openssl/include/openssl/md4.h b/openssl/include/openssl/md4.h index 4ff863e7f..4ff863e7f 100644..120000 --- a/openssl/include/openssl/md4.h +++ b/openssl/include/openssl/md4.h diff --git a/openssl/include/openssl/md5.h b/openssl/include/openssl/md5.h index 26fa47eb5..26fa47eb5 100644..120000 --- a/openssl/include/openssl/md5.h +++ b/openssl/include/openssl/md5.h diff --git a/openssl/include/openssl/mdc2.h b/openssl/include/openssl/mdc2.h index 0bc32f121..0bc32f121 100644..120000 --- a/openssl/include/openssl/mdc2.h +++ b/openssl/include/openssl/mdc2.h diff --git a/openssl/include/openssl/modes.h b/openssl/include/openssl/modes.h index ccc172827..ccc172827 100644..120000 --- a/openssl/include/openssl/modes.h +++ b/openssl/include/openssl/modes.h diff --git a/openssl/include/openssl/obj_mac.h b/openssl/include/openssl/obj_mac.h index 0f443c828..0f443c828 100644..120000 --- a/openssl/include/openssl/obj_mac.h +++ b/openssl/include/openssl/obj_mac.h diff --git a/openssl/include/openssl/objects.h b/openssl/include/openssl/objects.h index 7bd145ca0..7bd145ca0 100644..120000 --- a/openssl/include/openssl/objects.h +++ b/openssl/include/openssl/objects.h diff --git a/openssl/include/openssl/ocsp.h b/openssl/include/openssl/ocsp.h index 08288c84a..08288c84a 100644..120000 --- a/openssl/include/openssl/ocsp.h +++ b/openssl/include/openssl/ocsp.h diff --git a/openssl/include/openssl/opensslconf.h b/openssl/include/openssl/opensslconf.h index 25d2bea96..25d2bea96 100644..120000 --- a/openssl/include/openssl/opensslconf.h +++ b/openssl/include/openssl/opensslconf.h diff --git a/openssl/include/openssl/opensslv.h b/openssl/include/openssl/opensslv.h index f314f5fc7..f314f5fc7 100644..120000 --- a/openssl/include/openssl/opensslv.h +++ b/openssl/include/openssl/opensslv.h diff --git a/openssl/include/openssl/ossl_typ.h b/openssl/include/openssl/ossl_typ.h index e8f42456e..e8f42456e 100644..120000 --- a/openssl/include/openssl/ossl_typ.h +++ b/openssl/include/openssl/ossl_typ.h diff --git a/openssl/include/openssl/pem.h b/openssl/include/openssl/pem.h index ca371423e..ca371423e 100644..120000 --- a/openssl/include/openssl/pem.h +++ b/openssl/include/openssl/pem.h diff --git a/openssl/include/openssl/pem2.h b/openssl/include/openssl/pem2.h index c734dbdc3..c734dbdc3 100644..120000 --- a/openssl/include/openssl/pem2.h +++ b/openssl/include/openssl/pem2.h diff --git a/openssl/include/openssl/pkcs12.h b/openssl/include/openssl/pkcs12.h index eebba7778..eebba7778 100644..120000 --- a/openssl/include/openssl/pkcs12.h +++ b/openssl/include/openssl/pkcs12.h diff --git a/openssl/include/openssl/pkcs7.h b/openssl/include/openssl/pkcs7.h index 73e1b23f7..73e1b23f7 100644..120000 --- a/openssl/include/openssl/pkcs7.h +++ b/openssl/include/openssl/pkcs7.h diff --git a/openssl/include/openssl/pqueue.h b/openssl/include/openssl/pqueue.h index 93817c2df..93817c2df 100644..120000 --- a/openssl/include/openssl/pqueue.h +++ b/openssl/include/openssl/pqueue.h diff --git a/openssl/include/openssl/rand.h b/openssl/include/openssl/rand.h index 11231f852..11231f852 100644..120000 --- a/openssl/include/openssl/rand.h +++ b/openssl/include/openssl/rand.h diff --git a/openssl/include/openssl/rc2.h b/openssl/include/openssl/rc2.h index bb5a05c5d..bb5a05c5d 100644..120000 --- a/openssl/include/openssl/rc2.h +++ b/openssl/include/openssl/rc2.h diff --git a/openssl/include/openssl/rc4.h b/openssl/include/openssl/rc4.h index ef7deeb7d..ef7deeb7d 100644..120000 --- a/openssl/include/openssl/rc4.h +++ b/openssl/include/openssl/rc4.h diff --git a/openssl/include/openssl/ripemd.h b/openssl/include/openssl/ripemd.h index 200f562fa..200f562fa 100644..120000 --- a/openssl/include/openssl/ripemd.h +++ b/openssl/include/openssl/ripemd.h diff --git a/openssl/include/openssl/rsa.h b/openssl/include/openssl/rsa.h index 3e5a65475..3e5a65475 100644..120000 --- a/openssl/include/openssl/rsa.h +++ b/openssl/include/openssl/rsa.h diff --git a/openssl/include/openssl/safestack.h b/openssl/include/openssl/safestack.h index 8ca5b4cc7..8ca5b4cc7 100644..120000 --- a/openssl/include/openssl/safestack.h +++ b/openssl/include/openssl/safestack.h diff --git a/openssl/include/openssl/seed.h b/openssl/include/openssl/seed.h index 05d04a50b..05d04a50b 100644..120000 --- a/openssl/include/openssl/seed.h +++ b/openssl/include/openssl/seed.h diff --git a/openssl/include/openssl/sha.h b/openssl/include/openssl/sha.h index 3025cd5d7..3025cd5d7 100644..120000 --- a/openssl/include/openssl/sha.h +++ b/openssl/include/openssl/sha.h diff --git a/openssl/include/openssl/srp.h b/openssl/include/openssl/srp.h index 16b73ebd3..16b73ebd3 100644..120000 --- a/openssl/include/openssl/srp.h +++ b/openssl/include/openssl/srp.h diff --git a/openssl/include/openssl/srtp.h b/openssl/include/openssl/srtp.h index 9800e4ee4..9800e4ee4 100644..120000 --- a/openssl/include/openssl/srtp.h +++ b/openssl/include/openssl/srtp.h diff --git a/openssl/include/openssl/ssl.h b/openssl/include/openssl/ssl.h index e87d9be8f..e87d9be8f 100644..120000 --- a/openssl/include/openssl/ssl.h +++ b/openssl/include/openssl/ssl.h diff --git a/openssl/include/openssl/ssl2.h b/openssl/include/openssl/ssl2.h index 72876883c..72876883c 100644..120000 --- a/openssl/include/openssl/ssl2.h +++ b/openssl/include/openssl/ssl2.h diff --git a/openssl/include/openssl/ssl23.h b/openssl/include/openssl/ssl23.h index 5605052d7..5605052d7 100644..120000 --- a/openssl/include/openssl/ssl23.h +++ b/openssl/include/openssl/ssl23.h diff --git a/openssl/include/openssl/ssl3.h b/openssl/include/openssl/ssl3.h index 5ae2507f2..5ae2507f2 100644..120000 --- a/openssl/include/openssl/ssl3.h +++ b/openssl/include/openssl/ssl3.h diff --git a/openssl/include/openssl/stack.h b/openssl/include/openssl/stack.h index 61d342fcd..61d342fcd 100644..120000 --- a/openssl/include/openssl/stack.h +++ b/openssl/include/openssl/stack.h diff --git a/openssl/include/openssl/symhacks.h b/openssl/include/openssl/symhacks.h index 4a1a6913c..4a1a6913c 100644..120000 --- a/openssl/include/openssl/symhacks.h +++ b/openssl/include/openssl/symhacks.h diff --git a/openssl/include/openssl/tls1.h b/openssl/include/openssl/tls1.h index 53d998fbd..53d998fbd 100644..120000 --- a/openssl/include/openssl/tls1.h +++ b/openssl/include/openssl/tls1.h diff --git a/openssl/include/openssl/ts.h b/openssl/include/openssl/ts.h index a75d99db1..a75d99db1 100644..120000 --- a/openssl/include/openssl/ts.h +++ b/openssl/include/openssl/ts.h diff --git a/openssl/include/openssl/txt_db.h b/openssl/include/openssl/txt_db.h index f672e3552..f672e3552 100644..120000 --- a/openssl/include/openssl/txt_db.h +++ b/openssl/include/openssl/txt_db.h diff --git a/openssl/include/openssl/ui.h b/openssl/include/openssl/ui.h index b07defad7..b07defad7 100644..120000 --- a/openssl/include/openssl/ui.h +++ b/openssl/include/openssl/ui.h diff --git a/openssl/include/openssl/ui_compat.h b/openssl/include/openssl/ui_compat.h index d8c74b7c5..d8c74b7c5 100644..120000 --- a/openssl/include/openssl/ui_compat.h +++ b/openssl/include/openssl/ui_compat.h diff --git a/openssl/include/openssl/whrlpool.h b/openssl/include/openssl/whrlpool.h index 125a0816f..125a0816f 100644..120000 --- a/openssl/include/openssl/whrlpool.h +++ b/openssl/include/openssl/whrlpool.h diff --git a/openssl/include/openssl/x509.h b/openssl/include/openssl/x509.h index b2b85c524..b2b85c524 100644..120000 --- a/openssl/include/openssl/x509.h +++ b/openssl/include/openssl/x509.h diff --git a/openssl/include/openssl/x509_vfy.h b/openssl/include/openssl/x509_vfy.h index bb99ad498..bb99ad498 100644..120000 --- a/openssl/include/openssl/x509_vfy.h +++ b/openssl/include/openssl/x509_vfy.h diff --git a/openssl/include/openssl/x509v3.h b/openssl/include/openssl/x509v3.h index 63d12f9dc..63d12f9dc 100644..120000 --- a/openssl/include/openssl/x509v3.h +++ b/openssl/include/openssl/x509v3.h diff --git a/openssl/openssl.spec b/openssl/openssl.spec index 44147ce64..f0f5ea8bc 100644 --- a/openssl/openssl.spec +++ b/openssl/openssl.spec @@ -7,7 +7,7 @@ Release: 1 Summary: Secure Sockets Layer and cryptography libraries and tools Name: openssl #Version: %{libmaj}.%{libmin}.%{librel} -Version: 1.0.1g +Version: 1.0.1h Source0: ftp://ftp.openssl.org/source/%{name}-%{version}.tar.gz License: OpenSSL Group: System Environment/Libraries diff --git a/openssl/ssl/Makefile b/openssl/ssl/Makefile index debe07405..0045d8983 100644 --- a/openssl/ssl/Makefile +++ b/openssl/ssl/Makefile @@ -15,7 +15,7 @@ KRB5_INCLUDES= CFLAGS= $(INCLUDES) $(CFLAG) GENERAL=Makefile README ssl-lib.com install.com -TEST=ssltest.c +TEST=ssltest.c heartbeat_test.c APPS= LIB=$(TOP)/libssl.a diff --git a/openssl/ssl/d1_both.c b/openssl/ssl/d1_both.c index 2e8cf681e..04aa23107 100644 --- a/openssl/ssl/d1_both.c +++ b/openssl/ssl/d1_both.c @@ -627,7 +627,16 @@ dtls1_reassemble_fragment(SSL *s, struct hm_header_st* msg_hdr, int *ok) frag->msg_header.frag_off = 0; } else + { frag = (hm_fragment*) item->data; + if (frag->msg_header.msg_len != msg_hdr->msg_len) + { + item = NULL; + frag = NULL; + goto err; + } + } + /* If message is already reassembled, this must be a * retransmit and can be dropped. @@ -674,8 +683,8 @@ dtls1_reassemble_fragment(SSL *s, struct hm_header_st* msg_hdr, int *ok) item = pitem_new(seq64be, frag); if (item == NULL) { - goto err; i = -1; + goto err; } pqueue_insert(s->d1->buffered_messages, item); @@ -784,6 +793,7 @@ dtls1_get_message_fragment(SSL *s, int st1, int stn, long max, int *ok) int i,al; struct hm_header_st msg_hdr; + redo: /* see if we have the required fragment already */ if ((frag_len = dtls1_retrieve_buffered_fragment(s,max,ok)) || *ok) { @@ -842,8 +852,7 @@ dtls1_get_message_fragment(SSL *s, int st1, int stn, long max, int *ok) s->msg_callback_arg); s->init_num = 0; - return dtls1_get_message_fragment(s, st1, stn, - max, ok); + goto redo; } else /* Incorrectly formated Hello request */ { diff --git a/openssl/ssl/d1_lib.c b/openssl/ssl/d1_lib.c index 106939f24..6bde16fa2 100644 --- a/openssl/ssl/d1_lib.c +++ b/openssl/ssl/d1_lib.c @@ -176,9 +176,12 @@ static void dtls1_clear_queues(SSL *s) while ( (item = pqueue_pop(s->d1->buffered_app_data.q)) != NULL) { - frag = (hm_fragment *)item->data; - OPENSSL_free(frag->fragment); - OPENSSL_free(frag); + rdata = (DTLS1_RECORD_DATA *) item->data; + if (rdata->rbuf.buf) + { + OPENSSL_free(rdata->rbuf.buf); + } + OPENSSL_free(item->data); pitem_free(item); } } diff --git a/openssl/ssl/d1_pkt.c b/openssl/ssl/d1_pkt.c index 8186462d4..438c0913d 100644 --- a/openssl/ssl/d1_pkt.c +++ b/openssl/ssl/d1_pkt.c @@ -239,14 +239,6 @@ dtls1_buffer_record(SSL *s, record_pqueue *queue, unsigned char *priority) } #endif - /* insert should not fail, since duplicates are dropped */ - if (pqueue_insert(queue->q, item) == NULL) - { - OPENSSL_free(rdata); - pitem_free(item); - return(0); - } - s->packet = NULL; s->packet_length = 0; memset(&(s->s3->rbuf), 0, sizeof(SSL3_BUFFER)); @@ -259,7 +251,16 @@ dtls1_buffer_record(SSL *s, record_pqueue *queue, unsigned char *priority) pitem_free(item); return(0); } - + + /* insert should not fail, since duplicates are dropped */ + if (pqueue_insert(queue->q, item) == NULL) + { + SSLerr(SSL_F_DTLS1_BUFFER_RECORD, ERR_R_INTERNAL_ERROR); + OPENSSL_free(rdata); + pitem_free(item); + return(0); + } + return(1); } diff --git a/openssl/ssl/d1_srvr.c b/openssl/ssl/d1_srvr.c index 9975e2087..1384ab0cb 100644 --- a/openssl/ssl/d1_srvr.c +++ b/openssl/ssl/d1_srvr.c @@ -1356,6 +1356,7 @@ int dtls1_send_server_key_exchange(SSL *s) (unsigned char *)encodedPoint, encodedlen); OPENSSL_free(encodedPoint); + encodedPoint = NULL; p += encodedlen; } #endif diff --git a/openssl/ssl/heartbeat_test.c b/openssl/ssl/heartbeat_test.c new file mode 100644 index 000000000..d8cc55998 --- /dev/null +++ b/openssl/ssl/heartbeat_test.c @@ -0,0 +1,465 @@ +/* test/heartbeat_test.c */ +/* + * Unit test for TLS heartbeats. + * + * Acts as a regression test against the Heartbleed bug (CVE-2014-0160). + * + * Author: Mike Bland (mbland@acm.org, http://mike-bland.com/) + * Date: 2014-04-12 + * License: Creative Commons Attribution 4.0 International (CC By 4.0) + * http://creativecommons.org/licenses/by/4.0/deed.en_US + * + * OUTPUT + * ------ + * The program returns zero on success. It will print a message with a count + * of the number of failed tests and return nonzero if any tests fail. + * + * It will print the contents of the request and response buffers for each + * failing test. In a "fixed" version, all the tests should pass and there + * should be no output. + * + * In a "bleeding" version, you'll see: + * + * test_dtls1_heartbleed failed: + * expected payload len: 0 + * received: 1024 + * sent 26 characters + * "HEARTBLEED " + * received 1024 characters + * "HEARTBLEED \xde\xad\xbe\xef..." + * ** test_dtls1_heartbleed failed ** + * + * The contents of the returned buffer in the failing test will depend on the + * contents of memory on your machine. + * + * MORE INFORMATION + * ---------------- + * http://mike-bland.com/2014/04/12/heartbleed.html + * http://mike-bland.com/tags/heartbleed.html + */ + +#include "../ssl/ssl_locl.h" +#include <ctype.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +#if !defined(OPENSSL_NO_HEARTBEATS) && !defined(OPENSSL_SYS_WINDOWS) + +/* As per https://tools.ietf.org/html/rfc6520#section-4 */ +#define MIN_PADDING_SIZE 16 + +/* Maximum number of payload characters to print as test output */ +#define MAX_PRINTABLE_CHARACTERS 1024 + +typedef struct heartbeat_test_fixture + { + SSL_CTX *ctx; + SSL *s; + const char* test_case_name; + int (*process_heartbeat)(SSL* s); + unsigned char* payload; + int sent_payload_len; + int expected_return_value; + int return_payload_offset; + int expected_payload_len; + const char* expected_return_payload; + } HEARTBEAT_TEST_FIXTURE; + +static HEARTBEAT_TEST_FIXTURE set_up(const char* const test_case_name, + const SSL_METHOD* meth) + { + HEARTBEAT_TEST_FIXTURE fixture; + int setup_ok = 1; + memset(&fixture, 0, sizeof(fixture)); + fixture.test_case_name = test_case_name; + + fixture.ctx = SSL_CTX_new(meth); + if (!fixture.ctx) + { + fprintf(stderr, "Failed to allocate SSL_CTX for test: %s\n", + test_case_name); + setup_ok = 0; + goto fail; + } + + fixture.s = SSL_new(fixture.ctx); + if (!fixture.s) + { + fprintf(stderr, "Failed to allocate SSL for test: %s\n", test_case_name); + setup_ok = 0; + goto fail; + } + + if (!ssl_init_wbio_buffer(fixture.s, 1)) + { + fprintf(stderr, "Failed to set up wbio buffer for test: %s\n", + test_case_name); + setup_ok = 0; + goto fail; + } + + if (!ssl3_setup_buffers(fixture.s)) + { + fprintf(stderr, "Failed to setup buffers for test: %s\n", + test_case_name); + setup_ok = 0; + goto fail; + } + + /* Clear the memory for the return buffer, since this isn't automatically + * zeroed in opt mode and will cause spurious test failures that will change + * with each execution. + */ + memset(fixture.s->s3->wbuf.buf, 0, fixture.s->s3->wbuf.len); + + fail: + if (!setup_ok) + { + ERR_print_errors_fp(stderr); + exit(EXIT_FAILURE); + } + return fixture; + } + +static HEARTBEAT_TEST_FIXTURE set_up_dtls(const char* const test_case_name) + { + HEARTBEAT_TEST_FIXTURE fixture = set_up(test_case_name, + DTLSv1_server_method()); + fixture.process_heartbeat = dtls1_process_heartbeat; + + /* As per dtls1_get_record(), skipping the following from the beginning of + * the returned heartbeat message: + * type-1 byte; version-2 bytes; sequence number-8 bytes; length-2 bytes + * + * And then skipping the 1-byte type encoded by process_heartbeat for + * a total of 14 bytes, at which point we can grab the length and the + * payload we seek. + */ + fixture.return_payload_offset = 14; + return fixture; + } + +/* Needed by ssl3_write_bytes() */ +static int dummy_handshake(SSL* s) + { + return 1; + } + +static HEARTBEAT_TEST_FIXTURE set_up_tls(const char* const test_case_name) + { + HEARTBEAT_TEST_FIXTURE fixture = set_up(test_case_name, + TLSv1_server_method()); + fixture.process_heartbeat = tls1_process_heartbeat; + fixture.s->handshake_func = dummy_handshake; + + /* As per do_ssl3_write(), skipping the following from the beginning of + * the returned heartbeat message: + * type-1 byte; version-2 bytes; length-2 bytes + * + * And then skipping the 1-byte type encoded by process_heartbeat for + * a total of 6 bytes, at which point we can grab the length and the payload + * we seek. + */ + fixture.return_payload_offset = 6; + return fixture; + } + +static void tear_down(HEARTBEAT_TEST_FIXTURE fixture) + { + ERR_print_errors_fp(stderr); + SSL_free(fixture.s); + SSL_CTX_free(fixture.ctx); + } + +static void print_payload(const char* const prefix, + const unsigned char *payload, const int n) + { + const int end = n < MAX_PRINTABLE_CHARACTERS ? n + : MAX_PRINTABLE_CHARACTERS; + int i = 0; + + printf("%s %d character%s", prefix, n, n == 1 ? "" : "s"); + if (end != n) printf(" (first %d shown)", end); + printf("\n \""); + + for (; i != end; ++i) + { + const unsigned char c = payload[i]; + if (isprint(c)) fputc(c, stdout); + else printf("\\x%02x", c); + } + printf("\"\n"); + } + +static int execute_heartbeat(HEARTBEAT_TEST_FIXTURE fixture) + { + int result = 0; + SSL* s = fixture.s; + unsigned char *payload = fixture.payload; + unsigned char sent_buf[MAX_PRINTABLE_CHARACTERS + 1]; + int return_value; + unsigned const char *p; + int actual_payload_len; + + s->s3->rrec.data = payload; + s->s3->rrec.length = strlen((const char*)payload); + *payload++ = TLS1_HB_REQUEST; + s2n(fixture.sent_payload_len, payload); + + /* Make a local copy of the request, since it gets overwritten at some + * point */ + memcpy((char *)sent_buf, (const char*)payload, sizeof(sent_buf)); + + return_value = fixture.process_heartbeat(s); + + if (return_value != fixture.expected_return_value) + { + printf("%s failed: expected return value %d, received %d\n", + fixture.test_case_name, fixture.expected_return_value, + return_value); + result = 1; + } + + /* If there is any byte alignment, it will be stored in wbuf.offset. */ + p = &(s->s3->wbuf.buf[ + fixture.return_payload_offset + s->s3->wbuf.offset]); + actual_payload_len = 0; + n2s(p, actual_payload_len); + + if (actual_payload_len != fixture.expected_payload_len) + { + printf("%s failed:\n expected payload len: %d\n received: %d\n", + fixture.test_case_name, fixture.expected_payload_len, + actual_payload_len); + print_payload("sent", sent_buf, strlen((const char*)sent_buf)); + print_payload("received", p, actual_payload_len); + result = 1; + } + else + { + char* actual_payload = BUF_strndup((const char*)p, actual_payload_len); + if (strcmp(actual_payload, fixture.expected_return_payload) != 0) + { + printf("%s failed:\n expected payload: \"%s\"\n received: \"%s\"\n", + fixture.test_case_name, fixture.expected_return_payload, + actual_payload); + result = 1; + } + OPENSSL_free(actual_payload); + } + + if (result != 0) + { + printf("** %s failed **\n--------\n", fixture.test_case_name); + } + return result; + } + +static int honest_payload_size(unsigned char payload_buf[]) + { + /* Omit three-byte pad at the beginning for type and payload length */ + return strlen((const char*)&payload_buf[3]) - MIN_PADDING_SIZE; + } + +#define SETUP_HEARTBEAT_TEST_FIXTURE(type)\ + HEARTBEAT_TEST_FIXTURE fixture = set_up_##type(__func__);\ + int result = 0 + +#define EXECUTE_HEARTBEAT_TEST()\ + if (execute_heartbeat(fixture) != 0) result = 1;\ + tear_down(fixture);\ + return result + +static int test_dtls1_not_bleeding() + { + SETUP_HEARTBEAT_TEST_FIXTURE(dtls); + /* Three-byte pad at the beginning for type and payload length */ + unsigned char payload_buf[] = " Not bleeding, sixteen spaces of padding" + " "; + const int payload_buf_len = honest_payload_size(payload_buf); + + fixture.payload = &payload_buf[0]; + fixture.sent_payload_len = payload_buf_len; + fixture.expected_return_value = 0; + fixture.expected_payload_len = payload_buf_len; + fixture.expected_return_payload = "Not bleeding, sixteen spaces of padding"; + EXECUTE_HEARTBEAT_TEST(); + } + +static int test_dtls1_not_bleeding_empty_payload() + { + int payload_buf_len; + + SETUP_HEARTBEAT_TEST_FIXTURE(dtls); + /* Three-byte pad at the beginning for type and payload length, plus a NUL + * at the end */ + unsigned char payload_buf[4 + MIN_PADDING_SIZE]; + memset(payload_buf, ' ', sizeof(payload_buf)); + payload_buf[sizeof(payload_buf) - 1] = '\0'; + payload_buf_len = honest_payload_size(payload_buf); + + fixture.payload = &payload_buf[0]; + fixture.sent_payload_len = payload_buf_len; + fixture.expected_return_value = 0; + fixture.expected_payload_len = payload_buf_len; + fixture.expected_return_payload = ""; + EXECUTE_HEARTBEAT_TEST(); + } + +static int test_dtls1_heartbleed() + { + SETUP_HEARTBEAT_TEST_FIXTURE(dtls); + /* Three-byte pad at the beginning for type and payload length */ + unsigned char payload_buf[] = " HEARTBLEED "; + + fixture.payload = &payload_buf[0]; + fixture.sent_payload_len = MAX_PRINTABLE_CHARACTERS; + fixture.expected_return_value = 0; + fixture.expected_payload_len = 0; + fixture.expected_return_payload = ""; + EXECUTE_HEARTBEAT_TEST(); + } + +static int test_dtls1_heartbleed_empty_payload() + { + SETUP_HEARTBEAT_TEST_FIXTURE(dtls); + /* Excluding the NUL at the end, one byte short of type + payload length + + * minimum padding */ + unsigned char payload_buf[MIN_PADDING_SIZE + 3]; + memset(payload_buf, ' ', sizeof(payload_buf)); + payload_buf[sizeof(payload_buf) - 1] = '\0'; + + fixture.payload = &payload_buf[0]; + fixture.sent_payload_len = MAX_PRINTABLE_CHARACTERS; + fixture.expected_return_value = 0; + fixture.expected_payload_len = 0; + fixture.expected_return_payload = ""; + EXECUTE_HEARTBEAT_TEST(); + } + +static int test_dtls1_heartbleed_excessive_plaintext_length() + { + SETUP_HEARTBEAT_TEST_FIXTURE(dtls); + /* Excluding the NUL at the end, one byte in excess of maximum allowed + * heartbeat message length */ + unsigned char payload_buf[SSL3_RT_MAX_PLAIN_LENGTH + 2]; + memset(payload_buf, ' ', sizeof(payload_buf)); + payload_buf[sizeof(payload_buf) - 1] = '\0'; + + fixture.payload = &payload_buf[0]; + fixture.sent_payload_len = honest_payload_size(payload_buf); + fixture.expected_return_value = 0; + fixture.expected_payload_len = 0; + fixture.expected_return_payload = ""; + EXECUTE_HEARTBEAT_TEST(); + } + +static int test_tls1_not_bleeding() + { + SETUP_HEARTBEAT_TEST_FIXTURE(tls); + /* Three-byte pad at the beginning for type and payload length */ + unsigned char payload_buf[] = " Not bleeding, sixteen spaces of padding" + " "; + const int payload_buf_len = honest_payload_size(payload_buf); + + fixture.payload = &payload_buf[0]; + fixture.sent_payload_len = payload_buf_len; + fixture.expected_return_value = 0; + fixture.expected_payload_len = payload_buf_len; + fixture.expected_return_payload = "Not bleeding, sixteen spaces of padding"; + EXECUTE_HEARTBEAT_TEST(); + } + +static int test_tls1_not_bleeding_empty_payload() + { + int payload_buf_len; + + SETUP_HEARTBEAT_TEST_FIXTURE(tls); + /* Three-byte pad at the beginning for type and payload length, plus a NUL + * at the end */ + unsigned char payload_buf[4 + MIN_PADDING_SIZE]; + memset(payload_buf, ' ', sizeof(payload_buf)); + payload_buf[sizeof(payload_buf) - 1] = '\0'; + payload_buf_len = honest_payload_size(payload_buf); + + fixture.payload = &payload_buf[0]; + fixture.sent_payload_len = payload_buf_len; + fixture.expected_return_value = 0; + fixture.expected_payload_len = payload_buf_len; + fixture.expected_return_payload = ""; + EXECUTE_HEARTBEAT_TEST(); + } + +static int test_tls1_heartbleed() + { + SETUP_HEARTBEAT_TEST_FIXTURE(tls); + /* Three-byte pad at the beginning for type and payload length */ + unsigned char payload_buf[] = " HEARTBLEED "; + + fixture.payload = &payload_buf[0]; + fixture.sent_payload_len = MAX_PRINTABLE_CHARACTERS; + fixture.expected_return_value = 0; + fixture.expected_payload_len = 0; + fixture.expected_return_payload = ""; + EXECUTE_HEARTBEAT_TEST(); + } + +static int test_tls1_heartbleed_empty_payload() + { + SETUP_HEARTBEAT_TEST_FIXTURE(tls); + /* Excluding the NUL at the end, one byte short of type + payload length + + * minimum padding */ + unsigned char payload_buf[MIN_PADDING_SIZE + 3]; + memset(payload_buf, ' ', sizeof(payload_buf)); + payload_buf[sizeof(payload_buf) - 1] = '\0'; + + fixture.payload = &payload_buf[0]; + fixture.sent_payload_len = MAX_PRINTABLE_CHARACTERS; + fixture.expected_return_value = 0; + fixture.expected_payload_len = 0; + fixture.expected_return_payload = ""; + EXECUTE_HEARTBEAT_TEST(); + } + +#undef EXECUTE_HEARTBEAT_TEST +#undef SETUP_HEARTBEAT_TEST_FIXTURE + +int main(int argc, char *argv[]) + { + int num_failed; + + SSL_library_init(); + SSL_load_error_strings(); + + num_failed = test_dtls1_not_bleeding() + + test_dtls1_not_bleeding_empty_payload() + + test_dtls1_heartbleed() + + test_dtls1_heartbleed_empty_payload() + + /* The following test causes an assertion failure at + * ssl/d1_pkt.c:dtls1_write_bytes() in versions prior to 1.0.1g: */ + (OPENSSL_VERSION_NUMBER >= 0x1000107fL ? + test_dtls1_heartbleed_excessive_plaintext_length() : 0) + + test_tls1_not_bleeding() + + test_tls1_not_bleeding_empty_payload() + + test_tls1_heartbleed() + + test_tls1_heartbleed_empty_payload() + + 0; + + ERR_print_errors_fp(stderr); + + if (num_failed != 0) + { + printf("%d test%s failed\n", num_failed, num_failed != 1 ? "s" : ""); + return EXIT_FAILURE; + } + return EXIT_SUCCESS; + } + +#else /* OPENSSL_NO_HEARTBEATS*/ + +int main(int argc, char *argv[]) + { + return EXIT_SUCCESS; + } +#endif /* OPENSSL_NO_HEARTBEATS */ diff --git a/openssl/ssl/s3_clnt.c b/openssl/ssl/s3_clnt.c index a6b3c01af..0457af878 100644 --- a/openssl/ssl/s3_clnt.c +++ b/openssl/ssl/s3_clnt.c @@ -559,6 +559,7 @@ int ssl3_connect(SSL *s) case SSL3_ST_CR_FINISHED_A: case SSL3_ST_CR_FINISHED_B: + s->s3->flags |= SSL3_FLAGS_CCS_OK; ret=ssl3_get_finished(s,SSL3_ST_CR_FINISHED_A, SSL3_ST_CR_FINISHED_B); if (ret <= 0) goto end; @@ -915,6 +916,7 @@ int ssl3_get_server_hello(SSL *s) SSLerr(SSL_F_SSL3_GET_SERVER_HELLO,SSL_R_ATTEMPT_TO_REUSE_SESSION_IN_DIFFERENT_CONTEXT); goto f_err; } + s->s3->flags |= SSL3_FLAGS_CCS_OK; s->hit=1; } else /* a miss or crap from the other end */ @@ -2510,6 +2512,13 @@ int ssl3_send_client_key_exchange(SSL *s) int ecdh_clnt_cert = 0; int field_size = 0; + if (s->session->sess_cert == NULL) + { + ssl3_send_alert(s,SSL3_AL_FATAL,SSL_AD_UNEXPECTED_MESSAGE); + SSLerr(SSL_F_SSL3_SEND_CLIENT_KEY_EXCHANGE,SSL_R_UNEXPECTED_MESSAGE); + goto err; + } + /* Did we send out the client's * ECDH share for use in premaster * computation as part of client certificate? diff --git a/openssl/ssl/s3_pkt.c b/openssl/ssl/s3_pkt.c index 96ba63262..59011e39c 100644 --- a/openssl/ssl/s3_pkt.c +++ b/openssl/ssl/s3_pkt.c @@ -110,6 +110,7 @@ */ #include <stdio.h> +#include <limits.h> #include <errno.h> #define USE_SOCKETS #include "ssl_locl.h" @@ -580,10 +581,11 @@ int ssl3_do_compress(SSL *ssl) int ssl3_write_bytes(SSL *s, int type, const void *buf_, int len) { const unsigned char *buf=buf_; - unsigned int tot,n,nw; - int i; + unsigned int n,nw; + int i,tot; s->rwstate=SSL_NOTHING; + OPENSSL_assert(s->s3->wnum <= INT_MAX); tot=s->s3->wnum; s->s3->wnum=0; @@ -598,6 +600,22 @@ int ssl3_write_bytes(SSL *s, int type, const void *buf_, int len) } } + /* ensure that if we end up with a smaller value of data to write + * out than the the original len from a write which didn't complete + * for non-blocking I/O and also somehow ended up avoiding + * the check for this in ssl3_write_pending/SSL_R_BAD_WRITE_RETRY as + * it must never be possible to end up with (len-tot) as a large + * number that will then promptly send beyond the end of the users + * buffer ... so we trap and report the error in a way the user + * will notice + */ + if (len < tot) + { + SSLerr(SSL_F_SSL3_WRITE_BYTES,SSL_R_BAD_LENGTH); + return(-1); + } + + n=(len-tot); for (;;) { @@ -641,9 +659,6 @@ static int do_ssl3_write(SSL *s, int type, const unsigned char *buf, SSL3_BUFFER *wb=&(s->s3->wbuf); SSL_SESSION *sess; - if (wb->buf == NULL) - if (!ssl3_setup_write_buffer(s)) - return -1; /* first check if there is a SSL3_BUFFER still being written * out. This will happen with non blocking IO */ @@ -659,6 +674,10 @@ static int do_ssl3_write(SSL *s, int type, const unsigned char *buf, /* if it went, fall through and send more stuff */ } + if (wb->buf == NULL) + if (!ssl3_setup_write_buffer(s)) + return -1; + if (len == 0 && !create_empty_fragment) return 0; @@ -1055,7 +1074,7 @@ start: { s->rstate=SSL_ST_READ_HEADER; rr->off=0; - if (s->mode & SSL_MODE_RELEASE_BUFFERS) + if (s->mode & SSL_MODE_RELEASE_BUFFERS && s->s3->rbuf.left == 0) ssl3_release_read_buffer(s); } } @@ -1297,6 +1316,15 @@ start: goto f_err; } + if (!(s->s3->flags & SSL3_FLAGS_CCS_OK)) + { + al=SSL_AD_UNEXPECTED_MESSAGE; + SSLerr(SSL_F_SSL3_READ_BYTES,SSL_R_CCS_RECEIVED_EARLY); + goto f_err; + } + + s->s3->flags &= ~SSL3_FLAGS_CCS_OK; + rr->length=0; if (s->msg_callback) @@ -1431,7 +1459,7 @@ int ssl3_do_change_cipher_spec(SSL *s) if (s->s3->tmp.key_block == NULL) { - if (s->session == NULL) + if (s->session == NULL || s->session->master_key_length == 0) { /* might happen if dtls1_read_bytes() calls this */ SSLerr(SSL_F_SSL3_DO_CHANGE_CIPHER_SPEC,SSL_R_CCS_RECEIVED_EARLY); diff --git a/openssl/ssl/s3_srvr.c b/openssl/ssl/s3_srvr.c index 9ac19c05f..503bed3fe 100644 --- a/openssl/ssl/s3_srvr.c +++ b/openssl/ssl/s3_srvr.c @@ -673,6 +673,7 @@ int ssl3_accept(SSL *s) case SSL3_ST_SR_CERT_VRFY_A: case SSL3_ST_SR_CERT_VRFY_B: + s->s3->flags |= SSL3_FLAGS_CCS_OK; /* we should decide if we expected this one */ ret=ssl3_get_cert_verify(s); if (ret <= 0) goto end; @@ -700,6 +701,7 @@ int ssl3_accept(SSL *s) case SSL3_ST_SR_FINISHED_A: case SSL3_ST_SR_FINISHED_B: + s->s3->flags |= SSL3_FLAGS_CCS_OK; ret=ssl3_get_finished(s,SSL3_ST_SR_FINISHED_A, SSL3_ST_SR_FINISHED_B); if (ret <= 0) goto end; @@ -770,7 +772,10 @@ int ssl3_accept(SSL *s) s->s3->tmp.next_state=SSL3_ST_SR_FINISHED_A; #else if (s->s3->next_proto_neg_seen) + { + s->s3->flags |= SSL3_FLAGS_CCS_OK; s->s3->tmp.next_state=SSL3_ST_SR_NEXT_PROTO_A; + } else s->s3->tmp.next_state=SSL3_ST_SR_FINISHED_A; #endif @@ -2097,6 +2102,11 @@ int ssl3_send_certificate_request(SSL *s) s->init_num=n+4; s->init_off=0; #ifdef NETSCAPE_HANG_BUG + if (!BUF_MEM_grow_clean(buf, s->init_num + 4)) + { + SSLerr(SSL_F_SSL3_SEND_CERTIFICATE_REQUEST,ERR_R_BUF_LIB); + goto err; + } p=(unsigned char *)s->init_buf->data + s->init_num; /* do the header */ @@ -2813,6 +2823,8 @@ int ssl3_get_client_key_exchange(SSL *s) unsigned char premaster_secret[32], *start; size_t outlen=32, inlen; unsigned long alg_a; + int Ttag, Tclass; + long Tlen; /* Get our certificate private key*/ alg_a = s->s3->tmp.new_cipher->algorithm_auth; @@ -2834,26 +2846,15 @@ int ssl3_get_client_key_exchange(SSL *s) ERR_clear_error(); } /* Decrypt session key */ - if ((*p!=( V_ASN1_SEQUENCE| V_ASN1_CONSTRUCTED))) - { - SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE,SSL_R_DECRYPTION_FAILED); - goto gerr; - } - if (p[1] == 0x81) - { - start = p+3; - inlen = p[2]; - } - else if (p[1] < 0x80) - { - start = p+2; - inlen = p[1]; - } - else + if (ASN1_get_object((const unsigned char **)&p, &Tlen, &Ttag, &Tclass, n) != V_ASN1_CONSTRUCTED || + Ttag != V_ASN1_SEQUENCE || + Tclass != V_ASN1_UNIVERSAL) { SSLerr(SSL_F_SSL3_GET_CLIENT_KEY_EXCHANGE,SSL_R_DECRYPTION_FAILED); goto gerr; } + start = p; + inlen = Tlen; if (EVP_PKEY_decrypt(pkey_ctx,premaster_secret,&outlen,start,inlen) <=0) { diff --git a/openssl/ssl/ssl-lib.com b/openssl/ssl/ssl-lib.com index c7bc6fbd7..05bda755b 100644 --- a/openssl/ssl/ssl-lib.com +++ b/openssl/ssl/ssl-lib.com @@ -857,7 +857,7 @@ $ CCDEFS = "TCPIP_TYPE_''P4'" $ IF F$TYPE(USER_CCDEFS) .NES. "" THEN CCDEFS = CCDEFS + "," + USER_CCDEFS $ CCEXTRAFLAGS = "" $ IF F$TYPE(USER_CCFLAGS) .NES. "" THEN CCEXTRAFLAGS = USER_CCFLAGS -$ CCDISABLEWARNINGS = "MAYLOSEDATA3" !!! "LONGLONGTYPE,LONGLONGSUFX,FOUNDCR" +$ CCDISABLEWARNINGS = "" !!! "MAYLOSEDATA3" !!! "LONGLONGTYPE,LONGLONGSUFX,FOUNDCR" $ IF F$TYPE(USER_CCDISABLEWARNINGS) .NES. "" THEN - CCDISABLEWARNINGS = CCDISABLEWARNINGS + "," + USER_CCDISABLEWARNINGS $! @@ -1022,6 +1022,18 @@ $! Finish up the definition of CC. $! $ IF COMPILER .EQS. "DECC" $ THEN +$! Not all compiler versions support MAYLOSEDATA3. +$ OPT_TEST = "MAYLOSEDATA3" +$ DEFINE /USER_MODE SYS$ERROR NL: +$ DEFINE /USER_MODE SYS$OUTPUT NL: +$ 'CC' /NOCROSS_REFERENCE /NOLIST /NOOBJECT - + /WARNINGS = DISABLE = ('OPT_TEST', EMPTYFILE) NL: +$ IF ($SEVERITY) +$ THEN +$ IF CCDISABLEWARNINGS .NES. "" THEN - + CCDISABLEWARNINGS = CCDISABLEWARNINGS+ "," +$ CCDISABLEWARNINGS = CCDISABLEWARNINGS+ OPT_TEST +$ ENDIF $ IF CCDISABLEWARNINGS .EQS. "" $ THEN $ CC4DISABLEWARNINGS = "DOLLARID" diff --git a/openssl/ssl/ssl.h b/openssl/ssl/ssl.h index 7219a0e64..4c1242c9d 100644 --- a/openssl/ssl/ssl.h +++ b/openssl/ssl/ssl.h @@ -553,7 +553,7 @@ struct ssl_session_st /* Allow initial connection to servers that don't support RI */ #define SSL_OP_LEGACY_SERVER_CONNECT 0x00000004L #define SSL_OP_NETSCAPE_REUSE_CIPHER_CHANGE_BUG 0x00000008L -#define SSL_OP_SSLREF2_REUSE_CERT_TYPE_BUG 0x00000010L +#define SSL_OP_TLSEXT_PADDING 0x00000010L #define SSL_OP_MICROSOFT_BIG_SSLV3_BUFFER 0x00000020L #define SSL_OP_SAFARI_ECDHE_ECDSA_BUG 0x00000040L #define SSL_OP_SSLEAY_080_CLIENT_DH_BUG 0x00000080L @@ -562,6 +562,8 @@ struct ssl_session_st /* Hasn't done anything since OpenSSL 0.9.7h, retained for compatibility */ #define SSL_OP_MSIE_SSLV2_RSA_PADDING 0x0 +/* Refers to ancient SSLREF and SSLv2, retained for compatibility */ +#define SSL_OP_SSLREF2_REUSE_CERT_TYPE_BUG 0x0 /* Disable SSL 3.0/TLS 1.0 CBC vulnerability workaround that was added * in OpenSSL 0.9.6d. Usually (depending on the application protocol) diff --git a/openssl/ssl/ssl3.h b/openssl/ssl/ssl3.h index cb8b2492e..37f19e3ab 100644 --- a/openssl/ssl/ssl3.h +++ b/openssl/ssl/ssl3.h @@ -388,6 +388,7 @@ typedef struct ssl3_buffer_st #define TLS1_FLAGS_TLS_PADDING_BUG 0x0008 #define TLS1_FLAGS_SKIP_CERT_VERIFY 0x0010 #define TLS1_FLAGS_KEEP_HANDSHAKE 0x0020 +#define SSL3_FLAGS_CCS_OK 0x0080 /* SSL3_FLAGS_SGC_RESTART_DONE is set when we * restart a handshake because of MS SGC and so prevents us diff --git a/openssl/ssl/ssl_asn1.c b/openssl/ssl/ssl_asn1.c index 38540be1e..477500371 100644 --- a/openssl/ssl/ssl_asn1.c +++ b/openssl/ssl/ssl_asn1.c @@ -408,6 +408,7 @@ SSL_SESSION *d2i_SSL_SESSION(SSL_SESSION **a, const unsigned char **pp, if (os.length != 3) { c.error=SSL_R_CIPHER_CODE_WRONG_LENGTH; + c.line=__LINE__; goto err; } id=0x02000000L| @@ -420,6 +421,7 @@ SSL_SESSION *d2i_SSL_SESSION(SSL_SESSION **a, const unsigned char **pp, if (os.length != 2) { c.error=SSL_R_CIPHER_CODE_WRONG_LENGTH; + c.line=__LINE__; goto err; } id=0x03000000L| @@ -429,6 +431,7 @@ SSL_SESSION *d2i_SSL_SESSION(SSL_SESSION **a, const unsigned char **pp, else { c.error=SSL_R_UNKNOWN_SSL_VERSION; + c.line=__LINE__; goto err; } @@ -521,6 +524,7 @@ SSL_SESSION *d2i_SSL_SESSION(SSL_SESSION **a, const unsigned char **pp, if (os.length > SSL_MAX_SID_CTX_LENGTH) { c.error=SSL_R_BAD_LENGTH; + c.line=__LINE__; goto err; } else diff --git a/openssl/ssl/ssl_err.c b/openssl/ssl/ssl_err.c index 370fb57e3..49ab43e0e 100644 --- a/openssl/ssl/ssl_err.c +++ b/openssl/ssl/ssl_err.c @@ -541,7 +541,7 @@ static ERR_STRING_DATA SSL_str_reasons[]= {ERR_REASON(SSL_R_TLSV1_UNRECOGNIZED_NAME),"tlsv1 unrecognized name"}, {ERR_REASON(SSL_R_TLSV1_UNSUPPORTED_EXTENSION),"tlsv1 unsupported extension"}, {ERR_REASON(SSL_R_TLS_CLIENT_CERT_REQ_WITH_ANON_CIPHER),"tls client cert req with anon cipher"}, -{ERR_REASON(SSL_R_TLS_HEARTBEAT_PEER_DOESNT_ACCEPT),"peer does not accept heartbearts"}, +{ERR_REASON(SSL_R_TLS_HEARTBEAT_PEER_DOESNT_ACCEPT),"peer does not accept heartbeats"}, {ERR_REASON(SSL_R_TLS_HEARTBEAT_PENDING) ,"heartbeat request already pending"}, {ERR_REASON(SSL_R_TLS_ILLEGAL_EXPORTER_LABEL),"tls illegal exporter label"}, {ERR_REASON(SSL_R_TLS_INVALID_ECPOINTFORMAT_LIST),"tls invalid ecpointformat list"}, diff --git a/openssl/ssl/ssl_lib.c b/openssl/ssl/ssl_lib.c index 6dbc3c1f7..ef6258ca9 100644 --- a/openssl/ssl/ssl_lib.c +++ b/openssl/ssl/ssl_lib.c @@ -1349,6 +1349,10 @@ char *SSL_get_shared_ciphers(const SSL *s,char *buf,int len) p=buf; sk=s->session->ciphers; + + if (sk_SSL_CIPHER_num(sk) == 0) + return NULL; + for (i=0; i<sk_SSL_CIPHER_num(sk); i++) { int n; diff --git a/openssl/ssl/t1_enc.c b/openssl/ssl/t1_enc.c index 0c4cddedf..ac8c15399 100644 --- a/openssl/ssl/t1_enc.c +++ b/openssl/ssl/t1_enc.c @@ -1048,14 +1048,10 @@ int tls1_mac(SSL *ssl, unsigned char *md, int send) if (!stream_mac) EVP_MD_CTX_cleanup(&hmac); #ifdef TLS_DEBUG -printf("sec="); -{unsigned int z; for (z=0; z<md_size; z++) printf("%02X ",mac_sec[z]); printf("\n"); } printf("seq="); {int z; for (z=0; z<8; z++) printf("%02X ",seq[z]); printf("\n"); } -printf("buf="); -{int z; for (z=0; z<5; z++) printf("%02X ",buf[z]); printf("\n"); } printf("rec="); -{unsigned int z; for (z=0; z<rec->length; z++) printf("%02X ",buf[z]); printf("\n"); } +{unsigned int z; for (z=0; z<rec->length; z++) printf("%02X ",rec->data[z]); printf("\n"); } #endif if (ssl->version != DTLS1_VERSION && ssl->version != DTLS1_BAD_VER) @@ -1185,7 +1181,7 @@ int tls1_export_keying_material(SSL *s, unsigned char *out, size_t olen, if (memcmp(val, TLS_MD_KEY_EXPANSION_CONST, TLS_MD_KEY_EXPANSION_CONST_SIZE) == 0) goto err1; - rv = tls1_PRF(s->s3->tmp.new_cipher->algorithm2, + rv = tls1_PRF(ssl_get_algorithm2(s), val, vallen, NULL, 0, NULL, 0, diff --git a/openssl/ssl/t1_lib.c b/openssl/ssl/t1_lib.c index bddffd92c..3b8d5153e 100644 --- a/openssl/ssl/t1_lib.c +++ b/openssl/ssl/t1_lib.c @@ -617,6 +617,8 @@ unsigned char *ssl_add_clienthello_tlsext(SSL *s, unsigned char *p, unsigned cha #ifndef OPENSSL_NO_HEARTBEATS /* Add Heartbeat extension */ + if ((limit - ret - 4 - 1) < 0) + return NULL; s2n(TLSEXT_TYPE_heartbeat,ret); s2n(1,ret); /* Set mode: @@ -661,36 +663,35 @@ unsigned char *ssl_add_clienthello_tlsext(SSL *s, unsigned char *p, unsigned cha ret += el; } #endif - -#ifdef TLSEXT_TYPE_padding /* Add padding to workaround bugs in F5 terminators. * See https://tools.ietf.org/html/draft-agl-tls-padding-03 * * NB: because this code works out the length of all existing * extensions it MUST always appear last. */ - { - int hlen = ret - (unsigned char *)s->init_buf->data; - /* The code in s23_clnt.c to build ClientHello messages includes the - * 5-byte record header in the buffer, while the code in s3_clnt.c does - * not. */ - if (s->state == SSL23_ST_CW_CLNT_HELLO_A) - hlen -= 5; - if (hlen > 0xff && hlen < 0x200) + if (s->options & SSL_OP_TLSEXT_PADDING) { - hlen = 0x200 - hlen; - if (hlen >= 4) - hlen -= 4; - else - hlen = 0; + int hlen = ret - (unsigned char *)s->init_buf->data; + /* The code in s23_clnt.c to build ClientHello messages + * includes the 5-byte record header in the buffer, while + * the code in s3_clnt.c does not. + */ + if (s->state == SSL23_ST_CW_CLNT_HELLO_A) + hlen -= 5; + if (hlen > 0xff && hlen < 0x200) + { + hlen = 0x200 - hlen; + if (hlen >= 4) + hlen -= 4; + else + hlen = 0; - s2n(TLSEXT_TYPE_padding, ret); - s2n(hlen, ret); - memset(ret, 0, hlen); - ret += hlen; + s2n(TLSEXT_TYPE_padding, ret); + s2n(hlen, ret); + memset(ret, 0, hlen); + ret += hlen; + } } - } -#endif if ((extdatalen = ret-p-2)== 0) return p; @@ -845,6 +846,8 @@ unsigned char *ssl_add_serverhello_tlsext(SSL *s, unsigned char *p, unsigned cha /* Add Heartbeat extension if we've received one */ if (s->tlsext_heartbeat & SSL_TLSEXT_HB_ENABLED) { + if ((limit - ret - 4 - 1) < 0) + return NULL; s2n(TLSEXT_TYPE_heartbeat,ret); s2n(1,ret); /* Set mode: diff --git a/openssl/test/Makefile b/openssl/test/Makefile index 4c9eabcc2..005f2e8d6 100644 --- a/openssl/test/Makefile +++ b/openssl/test/Makefile @@ -63,6 +63,7 @@ IGETEST= igetest JPAKETEST= jpaketest SRPTEST= srptest ASN1TEST= asn1test +HEARTBEATTEST= heartbeat_test TESTS= alltests @@ -74,7 +75,7 @@ EXE= $(BNTEST)$(EXE_EXT) $(ECTEST)$(EXE_EXT) $(ECDSATEST)$(EXE_EXT) $(ECDHTEST) $(RANDTEST)$(EXE_EXT) $(DHTEST)$(EXE_EXT) $(ENGINETEST)$(EXE_EXT) \ $(BFTEST)$(EXE_EXT) $(CASTTEST)$(EXE_EXT) $(SSLTEST)$(EXE_EXT) $(EXPTEST)$(EXE_EXT) $(DSATEST)$(EXE_EXT) $(RSATEST)$(EXE_EXT) \ $(EVPTEST)$(EXE_EXT) $(IGETEST)$(EXE_EXT) $(JPAKETEST)$(EXE_EXT) $(SRPTEST)$(EXE_EXT) \ - $(ASN1TEST)$(EXE_EXT) + $(ASN1TEST)$(EXE_EXT) $(HEARTBEATTEST)$(EXE_EXT) # $(METHTEST)$(EXE_EXT) @@ -86,7 +87,8 @@ OBJ= $(BNTEST).o $(ECTEST).o $(ECDSATEST).o $(ECDHTEST).o $(IDEATEST).o \ $(MDC2TEST).o $(RMDTEST).o \ $(RANDTEST).o $(DHTEST).o $(ENGINETEST).o $(CASTTEST).o \ $(BFTEST).o $(SSLTEST).o $(DSATEST).o $(EXPTEST).o $(RSATEST).o \ - $(EVPTEST).o $(IGETEST).o $(JPAKETEST).o $(ASN1TEST).o + $(EVPTEST).o $(IGETEST).o $(JPAKETEST).o $(ASN1TEST).o $(HEARTBEATTEST).o + SRC= $(BNTEST).c $(ECTEST).c $(ECDSATEST).c $(ECDHTEST).c $(IDEATEST).c \ $(MD2TEST).c $(MD4TEST).c $(MD5TEST).c \ $(HMACTEST).c $(WPTEST).c \ @@ -94,7 +96,8 @@ SRC= $(BNTEST).c $(ECTEST).c $(ECDSATEST).c $(ECDHTEST).c $(IDEATEST).c \ $(DESTEST).c $(SHATEST).c $(SHA1TEST).c $(MDC2TEST).c $(RMDTEST).c \ $(RANDTEST).c $(DHTEST).c $(ENGINETEST).c $(CASTTEST).c \ $(BFTEST).c $(SSLTEST).c $(DSATEST).c $(EXPTEST).c $(RSATEST).c \ - $(EVPTEST).c $(IGETEST).c $(JPAKETEST).c $(SRPTEST).c $(ASN1TEST).c + $(EVPTEST).c $(IGETEST).c $(JPAKETEST).c $(SRPTEST).c $(ASN1TEST).c \ + $(HEARTBEATTEST).c EXHEADER= HEADER= $(EXHEADER) @@ -137,7 +140,7 @@ alltests: \ test_enc test_x509 test_rsa test_crl test_sid \ test_gen test_req test_pkcs7 test_verify test_dh test_dsa \ test_ss test_ca test_engine test_evp test_ssl test_tsa test_ige \ - test_jpake test_srp test_cms + test_jpake test_srp test_cms test_heartbeat test_evp: ../util/shlib_wrap.sh ./$(EVPTEST) evptests.txt @@ -227,7 +230,7 @@ test_bn: @../util/shlib_wrap.sh ./$(BNTEST) >tmp.bntest @echo quit >>tmp.bntest @echo "running bc" - @<tmp.bntest sh -c "`sh ./bctest ignore`" | $(PERL) -e '$$i=0; while (<STDIN>) {if (/^test (.*)/) {print STDERR "\nverify $$1";} elsif (!/^0$$/) {die "\nFailed! bc: $$_";} else {print STDERR "."; $$i++;}} print STDERR "\n$$i tests passed\n"' + @<tmp.bntest sh -c "`sh ./bctest ignore`" | $(PERL) -e '$$i=0; while (<STDIN>) {if (/^test (.*)/) {print STDERR "\nverify $$1";} elsif (!/^0\r?$$/) {die "\nFailed! bc: $$_";} else {print STDERR "."; $$i++;}} print STDERR "\n$$i tests passed\n"' @echo 'test a^b%c implementations' ../util/shlib_wrap.sh ./$(EXPTEST) @@ -318,6 +321,9 @@ test_srp: $(SRPTEST)$(EXE_EXT) @echo "Test SRP" ../util/shlib_wrap.sh ./srptest +test_heartbeat: $(HEARTBEATTEST)$(EXE_EXT) + ../util/shlib_wrap.sh ./$(HEARTBEATTEST) + lint: lint -DLINT $(INCLUDES) $(SRC)>fluff @@ -469,6 +475,9 @@ $(ASN1TEST)$(EXE_EXT): $(ASN1TEST).o $(DLIBCRYPTO) $(SRPTEST)$(EXE_EXT): $(SRPTEST).o $(DLIBCRYPTO) @target=$(SRPTEST); $(BUILD_CMD) +$(HEARTBEATTEST)$(EXE_EXT): $(HEARTBEATTEST).o $(DLIBCRYPTO) + @target=$(HEARTBEATTEST); $(BUILD_CMD) + #$(AESTEST).o: $(AESTEST).c # $(CC) -c $(CFLAGS) -DINTERMEDIATE_VALUE_KAT -DTRACE_KAT_MCT $(AESTEST).c @@ -604,6 +613,27 @@ exptest.o: ../include/openssl/opensslconf.h ../include/openssl/opensslv.h exptest.o: ../include/openssl/ossl_typ.h ../include/openssl/rand.h exptest.o: ../include/openssl/safestack.h ../include/openssl/stack.h exptest.o: ../include/openssl/symhacks.h exptest.c +heartbeat_test.o: ../e_os.h ../include/openssl/asn1.h ../include/openssl/bio.h +heartbeat_test.o: ../include/openssl/buffer.h ../include/openssl/comp.h +heartbeat_test.o: ../include/openssl/crypto.h ../include/openssl/dsa.h +heartbeat_test.o: ../include/openssl/dtls1.h ../include/openssl/e_os2.h +heartbeat_test.o: ../include/openssl/ec.h ../include/openssl/ecdh.h +heartbeat_test.o: ../include/openssl/ecdsa.h ../include/openssl/err.h +heartbeat_test.o: ../include/openssl/evp.h ../include/openssl/hmac.h +heartbeat_test.o: ../include/openssl/kssl.h ../include/openssl/lhash.h +heartbeat_test.o: ../include/openssl/obj_mac.h ../include/openssl/objects.h +heartbeat_test.o: ../include/openssl/opensslconf.h +heartbeat_test.o: ../include/openssl/opensslv.h ../include/openssl/ossl_typ.h +heartbeat_test.o: ../include/openssl/pem.h ../include/openssl/pem2.h +heartbeat_test.o: ../include/openssl/pkcs7.h ../include/openssl/pqueue.h +heartbeat_test.o: ../include/openssl/rsa.h ../include/openssl/safestack.h +heartbeat_test.o: ../include/openssl/sha.h ../include/openssl/srtp.h +heartbeat_test.o: ../include/openssl/ssl.h ../include/openssl/ssl2.h +heartbeat_test.o: ../include/openssl/ssl23.h ../include/openssl/ssl3.h +heartbeat_test.o: ../include/openssl/stack.h ../include/openssl/symhacks.h +heartbeat_test.o: ../include/openssl/tls1.h ../include/openssl/x509.h +heartbeat_test.o: ../include/openssl/x509_vfy.h ../ssl/ssl_locl.h +heartbeat_test.o: heartbeat_test.c hmactest.o: ../e_os.h ../include/openssl/asn1.h ../include/openssl/bio.h hmactest.o: ../include/openssl/crypto.h ../include/openssl/e_os2.h hmactest.o: ../include/openssl/evp.h ../include/openssl/hmac.h diff --git a/openssl/test/bftest.c b/openssl/test/bftest.c index 78b1749a4..78b1749a4 100644..120000 --- a/openssl/test/bftest.c +++ b/openssl/test/bftest.c diff --git a/openssl/test/bntest.c b/openssl/test/bntest.c index 03f54a238..03f54a238 100644..120000 --- a/openssl/test/bntest.c +++ b/openssl/test/bntest.c diff --git a/openssl/test/casttest.c b/openssl/test/casttest.c index ac7ede8d7..ac7ede8d7 100644..120000 --- a/openssl/test/casttest.c +++ b/openssl/test/casttest.c diff --git a/openssl/test/destest.c b/openssl/test/destest.c index 5988c7303..5988c7303 100644..120000 --- a/openssl/test/destest.c +++ b/openssl/test/destest.c diff --git a/openssl/test/dhtest.c b/openssl/test/dhtest.c index 9a67f9162..9a67f9162 100644..120000 --- a/openssl/test/dhtest.c +++ b/openssl/test/dhtest.c diff --git a/openssl/test/dsatest.c b/openssl/test/dsatest.c index 16a1b5a34..16a1b5a34 100644..120000 --- a/openssl/test/dsatest.c +++ b/openssl/test/dsatest.c diff --git a/openssl/test/ecdhtest.c b/openssl/test/ecdhtest.c index 206d98686..206d98686 100644..120000 --- a/openssl/test/ecdhtest.c +++ b/openssl/test/ecdhtest.c diff --git a/openssl/test/ecdsatest.c b/openssl/test/ecdsatest.c index 441082ba2..441082ba2 100644..120000 --- a/openssl/test/ecdsatest.c +++ b/openssl/test/ecdsatest.c diff --git a/openssl/test/ectest.c b/openssl/test/ectest.c index df1831f81..df1831f81 100644..120000 --- a/openssl/test/ectest.c +++ b/openssl/test/ectest.c diff --git a/openssl/test/enginetest.c b/openssl/test/enginetest.c index 5c74a6f41..5c74a6f41 100644..120000 --- a/openssl/test/enginetest.c +++ b/openssl/test/enginetest.c diff --git a/openssl/test/evp_test.c b/openssl/test/evp_test.c index 074162812..074162812 100644..120000 --- a/openssl/test/evp_test.c +++ b/openssl/test/evp_test.c diff --git a/openssl/test/exptest.c b/openssl/test/exptest.c index 50ccf71cb..50ccf71cb 100644..120000 --- a/openssl/test/exptest.c +++ b/openssl/test/exptest.c diff --git a/openssl/test/heartbeat_test.c b/openssl/test/heartbeat_test.c new file mode 120000 index 000000000..79576fd5a --- /dev/null +++ b/openssl/test/heartbeat_test.c @@ -0,0 +1 @@ +../ssl/heartbeat_test.c
\ No newline at end of file diff --git a/openssl/test/hmactest.c b/openssl/test/hmactest.c index 353ee2c7f..353ee2c7f 100644..120000 --- a/openssl/test/hmactest.c +++ b/openssl/test/hmactest.c diff --git a/openssl/test/ideatest.c b/openssl/test/ideatest.c index a9bfb3d48..a9bfb3d48 100644..120000 --- a/openssl/test/ideatest.c +++ b/openssl/test/ideatest.c diff --git a/openssl/test/jpaketest.c b/openssl/test/jpaketest.c index 49f44f8b6..49f44f8b6 100644..120000 --- a/openssl/test/jpaketest.c +++ b/openssl/test/jpaketest.c diff --git a/openssl/test/md2test.c b/openssl/test/md2test.c index 49f44f8b6..49f44f8b6 100644..120000 --- a/openssl/test/md2test.c +++ b/openssl/test/md2test.c diff --git a/openssl/test/md4test.c b/openssl/test/md4test.c index 1509be911..1509be911 100644..120000 --- a/openssl/test/md4test.c +++ b/openssl/test/md4test.c diff --git a/openssl/test/md5test.c b/openssl/test/md5test.c index 20f4aaf0a..20f4aaf0a 100644..120000 --- a/openssl/test/md5test.c +++ b/openssl/test/md5test.c diff --git a/openssl/test/mdc2test.c b/openssl/test/mdc2test.c index c4ffe4835..c4ffe4835 100644..120000 --- a/openssl/test/mdc2test.c +++ b/openssl/test/mdc2test.c diff --git a/openssl/test/randtest.c b/openssl/test/randtest.c index a2b107a2b..a2b107a2b 100644..120000 --- a/openssl/test/randtest.c +++ b/openssl/test/randtest.c diff --git a/openssl/test/rc2test.c b/openssl/test/rc2test.c index 5c53ad984..5c53ad984 100644..120000 --- a/openssl/test/rc2test.c +++ b/openssl/test/rc2test.c diff --git a/openssl/test/rc4test.c b/openssl/test/rc4test.c index 061ac3773..061ac3773 100644..120000 --- a/openssl/test/rc4test.c +++ b/openssl/test/rc4test.c diff --git a/openssl/test/rc5test.c b/openssl/test/rc5test.c index 49f44f8b6..49f44f8b6 100644..120000 --- a/openssl/test/rc5test.c +++ b/openssl/test/rc5test.c diff --git a/openssl/test/rmdtest.c b/openssl/test/rmdtest.c index ce6646065..ce6646065 100644..120000 --- a/openssl/test/rmdtest.c +++ b/openssl/test/rmdtest.c diff --git a/openssl/test/rsa_test.c b/openssl/test/rsa_test.c index aaea20d98..aaea20d98 100644..120000 --- a/openssl/test/rsa_test.c +++ b/openssl/test/rsa_test.c diff --git a/openssl/test/sha1test.c b/openssl/test/sha1test.c index 8d66e9ee4..8d66e9ee4 100644..120000 --- a/openssl/test/sha1test.c +++ b/openssl/test/sha1test.c diff --git a/openssl/test/sha256t.c b/openssl/test/sha256t.c index 952a50867..952a50867 100644..120000 --- a/openssl/test/sha256t.c +++ b/openssl/test/sha256t.c diff --git a/openssl/test/sha512t.c b/openssl/test/sha512t.c index c80d152f1..c80d152f1 100644..120000 --- a/openssl/test/sha512t.c +++ b/openssl/test/sha512t.c diff --git a/openssl/test/shatest.c b/openssl/test/shatest.c index 43cfda78f..43cfda78f 100644..120000 --- a/openssl/test/shatest.c +++ b/openssl/test/shatest.c diff --git a/openssl/test/srptest.c b/openssl/test/srptest.c index 953486826..953486826 100644..120000 --- a/openssl/test/srptest.c +++ b/openssl/test/srptest.c diff --git a/openssl/test/ssltest.c b/openssl/test/ssltest.c index 40191f0da..40191f0da 100644..120000 --- a/openssl/test/ssltest.c +++ b/openssl/test/ssltest.c diff --git a/openssl/test/wp_test.c b/openssl/test/wp_test.c index 81b2021f3..81b2021f3 100644..120000 --- a/openssl/test/wp_test.c +++ b/openssl/test/wp_test.c diff --git a/packages.txt b/packages.txt index dd9b2e7d1..77e20ab17 100644 --- a/packages.txt +++ b/packages.txt @@ -66,7 +66,7 @@ libxcb git version libxkbfile-1.0.8
mesa git version
mkfontscale git version
-openssl-1.0.1g
+openssl-1.0.1h
pixman git version
presentproto-1.0
pthreads-w32 cvs version
diff --git a/xorg-server/configure.ac b/xorg-server/configure.ac index 0a6e77255..2daa6beec 100644 --- a/xorg-server/configure.ac +++ b/xorg-server/configure.ac @@ -810,7 +810,7 @@ LIBDMX="dmx >= 1.0.99.1" LIBDRI="dri >= 7.8.0" LIBDRM="libdrm >= 2.3.0" LIBEGL="egl" -LIBGBM="gbm >= 9" +LIBGBM="gbm >= 10.2.0" LIBGL="gl >= 7.1.0" LIBXEXT="xext >= 1.0.99.4" LIBXFONT="xfont >= 1.4.2" @@ -1424,7 +1424,7 @@ AC_DEFINE(SHAPE, 1, [Support SHAPE extension]) AC_DEFINE_DIR(XKB_BASE_DIRECTORY, XKBPATH, [Path to XKB data]) AC_ARG_WITH(xkb-bin-directory, - AS_HELP_STRING([--with-xkb-bin-directory=DIR], [Directory containing xkbcomp program]), + AS_HELP_STRING([--with-xkb-bin-directory=DIR], [Directory containing xkbcomp program (default: ${bindir})]), [XKB_BIN_DIRECTORY="$withval"], [XKB_BIN_DIRECTORY="$bindir"]) @@ -2459,6 +2459,10 @@ if test "x$XWAYLAND" = xyes; then XWAYLAND_SYS_LIBS="$XWAYLANDMODULES_LIBS $GLX_SYS_LIBS" AC_SUBST([XWAYLAND_LIBS]) AC_SUBST([XWAYLAND_SYS_LIBS]) + + WAYLAND_PREFIX=`$PKG_CONFIG --variable=prefix wayland-client` + AC_PATH_PROG([WAYLAND_SCANNER], [wayland-scanner],, + [${WAYLAND_PREFIX}/bin$PATH_SEPARATOR$PATH]) fi diff --git a/xorg-server/dix/getevents.c b/xorg-server/dix/getevents.c index 366bc9558..694a8eba3 100644 --- a/xorg-server/dix/getevents.c +++ b/xorg-server/dix/getevents.c @@ -781,27 +781,65 @@ add_to_scroll_valuator(DeviceIntPtr dev, ValuatorMask *mask, int valuator, doubl } +/* FIXME: relative events from devices with absolute axis ranges is + fundamentally broken. We map the device coordinate range into the screen + range, but don't really account for device resolution in that. + + what we do here is a hack to make touchpads usable. for a given relative + motion vector in device coordinates: + 1. calculate physical movement on the device in metres + 2. calculate pixel vector that is the same physical movement on the + screen (times some magic number to provide sensible base speed) + 3. calculate what percentage this vector is of the current screen + width/height + 4. calculate equivalent vector in % on the device's min/max axis range + 5. Use that device vector as the actual motion vector + + e.g. 10/50mm on the device, 10/50mm on the screen are 30/100 pixels, + 30/100 pixels are 1/3% of the width, 1/3% of the device is a vector of + 20/80 -> use 20/80 as dx/dy. + + dx/dy is then applied to the current position in device coordinates, + mapped to screen coordinates and thus the movement on the screen reflects + the motion direction on the device. + */ static void scale_for_device_resolution(DeviceIntPtr dev, ValuatorMask *mask) { - double y; + double x, y; ValuatorClassPtr v = dev->valuator; int xrange = v->axes[0].max_value - v->axes[0].min_value + 1; int yrange = v->axes[1].max_value - v->axes[1].min_value + 1; - double screen_ratio = 1.0 * screenInfo.width/screenInfo.height; - double device_ratio = 1.0 * xrange/yrange; - double resolution_ratio = 1.0; - double ratio; + /* Assume 100 units/m for devices without resolution */ + int xres = 100000, yres = 100000; - if (!valuator_mask_fetch_double(mask, 1, &y)) - return; + /* If we have multiple screens with different dpi, it gets complicated: + we have to map which screen we're on and then take the dpi of that + screen to be somewhat accurate. */ + const ScreenPtr s = screenInfo.screens[0]; + const double screen_res = 1000.0 * s->width/s->mmWidth; /* units/m */ - if (v->axes[0].resolution != 0 && v->axes[1].resolution != 0) - resolution_ratio = 1.0 * v->axes[0].resolution/v->axes[1].resolution; + /* some magic multiplier, so unaccelerated movement of x mm on the + device reflects x * magic mm on the screen */ + const double magic = 4; - ratio = device_ratio/resolution_ratio/screen_ratio; - valuator_mask_set_double(mask, 1, y / ratio); + if (v->axes[0].resolution != 0 && v->axes[1].resolution != 0) { + xres = v->axes[0].resolution; + yres = v->axes[1].resolution; + } + + if (valuator_mask_isset(mask, 0)) { + x = valuator_mask_get_double(mask, 0); + x = magic * x/xres * screen_res/screenInfo.width * xrange; + valuator_mask_set_double(mask, 0, x); + } + + if (valuator_mask_isset(mask, 1)) { + y = valuator_mask_get_double(mask, 1); + y = magic * y/yres * screen_res/screenInfo.height * yrange; + valuator_mask_set_double(mask, 1, y); + } } /** @@ -815,15 +853,6 @@ moveRelative(DeviceIntPtr dev, int flags, ValuatorMask *mask) { int i; Bool clip_xy = IsMaster(dev) || !IsFloating(dev); - ValuatorClassPtr v = dev->valuator; - - /* for abs devices in relative mode, we've just scaled wrong, since we - mapped the device's shape into the screen shape. Undo this. */ - if ((flags & POINTER_ABSOLUTE) == 0 && v && v->numAxes > 1 && - v->axes[0].min_value < v->axes[0].max_value && - v->axes[1].min_value < v->axes[1].max_value) { - scale_for_device_resolution(dev, mask); - } /* calc other axes, clip, drop back into valuators */ for (i = 0; i < valuator_mask_size(mask); i++) { @@ -1457,10 +1486,21 @@ fill_pointer_events(InternalEvent *events, DeviceIntPtr pDev, int type, set_raw_valuators(raw, &mask, raw->valuators.data); } else { + ValuatorClassPtr v = pDev->valuator; + transformRelative(pDev, &mask); + /* for abs devices in relative mode, we've just scaled wrong, since we + mapped the device's shape into the screen shape. Undo this. */ + if (v && v->numAxes > 1 && + v->axes[0].min_value < v->axes[0].max_value && + v->axes[1].min_value < v->axes[1].max_value) { + scale_for_device_resolution(pDev, &mask); + } + if (flags & POINTER_ACCELERATE) accelPointer(pDev, &mask, ms); + if ((flags & POINTER_NORAW) == 0 && raw) set_raw_valuators(raw, &mask, raw->valuators.data); diff --git a/xorg-server/exa/exa_unaccel.c b/xorg-server/exa/exa_unaccel.c index b66eeee7b..73fd3a3f5 100644 --- a/xorg-server/exa/exa_unaccel.c +++ b/xorg-server/exa/exa_unaccel.c @@ -685,7 +685,7 @@ ExaCheckAddTraps(PicturePtr pPicture, EXA_PRE_FALLBACK(pScreen); - EXA_FALLBACK(("to pict %p (%c)\n", + EXA_FALLBACK(("to pict %p (%c)\n", pPicture, exaDrawableLocation(pPicture->pDrawable))); exaPrepareAccess(pPicture->pDrawable, EXA_PREPARE_DEST); swap(pExaScr, ps, AddTraps); diff --git a/xorg-server/glamor/glamor.c b/xorg-server/glamor/glamor.c index 08f6ba174..c398807f1 100644 --- a/xorg-server/glamor/glamor.c +++ b/xorg-server/glamor/glamor.c @@ -316,6 +316,7 @@ glamor_init(ScreenPtr screen, unsigned int flags) { glamor_screen_private *glamor_priv; int gl_version; + int max_viewport_size; #ifdef RENDER PictureScreenPtr ps = GetPictureScreenIfSet(screen); @@ -406,7 +407,9 @@ glamor_init(ScreenPtr screen, unsigned int flags) epoxy_has_gl_extension("GL_ARB_map_buffer_range"); glamor_priv->has_buffer_storage = epoxy_has_gl_extension("GL_ARB_buffer_storage"); - glGetIntegerv(GL_MAX_RENDERBUFFER_SIZE, &glamor_priv->max_fbo_size); + glGetIntegerv(GL_MAX_TEXTURE_SIZE, &glamor_priv->max_fbo_size); + glGetIntegerv(GL_MAX_VIEWPORT_DIMS, &max_viewport_size); + glamor_priv->max_fbo_size = MIN(glamor_priv->max_fbo_size, max_viewport_size); #ifdef MAX_FBO_SIZE glamor_priv->max_fbo_size = MAX_FBO_SIZE; #endif diff --git a/xorg-server/glamor/glamor_fbo.c b/xorg-server/glamor/glamor_fbo.c index 552168381..090dfd8e7 100644 --- a/xorg-server/glamor/glamor_fbo.c +++ b/xorg-server/glamor/glamor_fbo.c @@ -347,6 +347,7 @@ _glamor_create_tex(glamor_screen_private *glamor_priv, glamor_make_current(glamor_priv); glGenTextures(1, &tex); glBindTexture(GL_TEXTURE_2D, tex); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 0); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glTexImage2D(GL_TEXTURE_2D, 0, format, w, h, 0, diff --git a/xorg-server/glamor/glamor_font.c b/xorg-server/glamor/glamor_font.c index f747d59a1..57c607dc2 100644 --- a/xorg-server/glamor/glamor_font.c +++ b/xorg-server/glamor/glamor_font.c @@ -95,6 +95,7 @@ glamor_font_get(ScreenPtr screen, FontPtr font) glActiveTexture(GL_TEXTURE0); glBindTexture(GL_TEXTURE_2D, glamor_font->texture_id); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 0); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); diff --git a/xorg-server/glamor/glamor_image.c b/xorg-server/glamor/glamor_image.c index 4791d089f..b38b41212 100644 --- a/xorg-server/glamor/glamor_image.c +++ b/xorg-server/glamor/glamor_image.c @@ -88,8 +88,7 @@ static void glamor_put_image_bail(DrawablePtr drawable, GCPtr gc, int depth, int x, int y, int w, int h, int leftPad, int format, char *bits) { - if (glamor_prepare_access(drawable, GLAMOR_ACCESS_RW) && - glamor_prepare_access_gc(gc)) + if (glamor_prepare_access(drawable, GLAMOR_ACCESS_RW)) fbPutImage(drawable, gc, depth, x, y, w, h, leftPad, format, bits); glamor_finish_access(drawable); } diff --git a/xorg-server/glamor/glamor_pixmap.c b/xorg-server/glamor/glamor_pixmap.c index 54b414bc2..789d3772e 100644 --- a/xorg-server/glamor/glamor_pixmap.c +++ b/xorg-server/glamor/glamor_pixmap.c @@ -717,6 +717,7 @@ __glamor_upload_pixmap_to_texture(PixmapPtr pixmap, unsigned int *tex, } glBindTexture(GL_TEXTURE_2D, *tex); + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 0); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glPixelStorei(GL_UNPACK_ALIGNMENT, 4); diff --git a/xorg-server/glamor/glamor_render.c b/xorg-server/glamor/glamor_render.c index 5a7a23880..14ab738eb 100644 --- a/xorg-server/glamor/glamor_render.c +++ b/xorg-server/glamor/glamor_render.c @@ -1450,8 +1450,8 @@ glamor_composite_clipped_region(CARD8 op, || source_pixmap->drawable.height != height)))) { temp_src = glamor_convert_gradient_picture(screen, source, - x_source, - y_source, + extent->x1 + x_source - x_dest, + extent->y1 + y_source - y_dest, width, height); if (!temp_src) { temp_src = source; @@ -1459,8 +1459,8 @@ glamor_composite_clipped_region(CARD8 op, } temp_src_priv = glamor_get_pixmap_private((PixmapPtr) (temp_src->pDrawable)); - x_temp_src = 0; - y_temp_src = 0; + x_temp_src = -extent->x1 + x_dest; + y_temp_src = -extent->y1 + y_dest; } if (mask @@ -1474,8 +1474,8 @@ glamor_composite_clipped_region(CARD8 op, * to do reduce one convertion. */ temp_mask = glamor_convert_gradient_picture(screen, mask, - x_mask, - y_mask, + extent->x1 + x_mask - x_dest, + extent->y1 + y_mask - y_dest, width, height); if (!temp_mask) { temp_mask = mask; @@ -1483,8 +1483,8 @@ glamor_composite_clipped_region(CARD8 op, } temp_mask_priv = glamor_get_pixmap_private((PixmapPtr) (temp_mask->pDrawable)); - x_temp_mask = 0; - y_temp_mask = 0; + x_temp_mask = -extent->x1 + x_dest; + y_temp_mask = -extent->y1 + y_dest; } /* Do two-pass PictOpOver componentAlpha, until we enable * dual source color blending. diff --git a/xorg-server/glamor/glamor_vbo.c b/xorg-server/glamor/glamor_vbo.c index c6785594b..e90610102 100644 --- a/xorg-server/glamor/glamor_vbo.c +++ b/xorg-server/glamor/glamor_vbo.c @@ -119,7 +119,7 @@ glamor_get_vbo_space(ScreenPtr screen, unsigned size, char **vbo_offset) if (glamor_priv->vbo_size < size) { glamor_priv->vbo_size = MAX(GLAMOR_VBO_SIZE, size); free(glamor_priv->vb); - glamor_priv->vb = XNFalloc(size); + glamor_priv->vb = XNFalloc(glamor_priv->vbo_size); } *vbo_offset = NULL; /* We point to the start of glamor_priv->vb every time, and diff --git a/xorg-server/hw/xfree86/dri2/dri2.c b/xorg-server/hw/xfree86/dri2/dri2.c index 6dd77963c..6459f11b1 100644 --- a/xorg-server/hw/xfree86/dri2/dri2.c +++ b/xorg-server/hw/xfree86/dri2/dri2.c @@ -130,6 +130,7 @@ typedef struct _DRI2Screen { HandleExposuresProcPtr HandleExposures; ConfigNotifyProcPtr ConfigNotify; + SetWindowPixmapProcPtr SetWindowPixmap; DRI2CreateBuffer2ProcPtr CreateBuffer2; DRI2DestroyBuffer2ProcPtr DestroyBuffer2; DRI2CopyRegion2ProcPtr CopyRegion2; @@ -415,18 +416,14 @@ DRI2DrawableGone(void *p, XID id) } static DRI2BufferPtr -create_buffer(DrawablePtr pDraw, +create_buffer(DRI2ScreenPtr ds, DrawablePtr pDraw, unsigned int attachment, unsigned int format) { - ScreenPtr primeScreen; - DRI2DrawablePtr pPriv; - DRI2ScreenPtr ds; DRI2BufferPtr buffer; - pPriv = DRI2GetDrawable(pDraw); - primeScreen = GetScreenPrime(pDraw->pScreen, pPriv->prime_id); - ds = DRI2GetScreenPrime(pDraw->pScreen, pPriv->prime_id); if (ds->CreateBuffer2) - buffer = (*ds->CreateBuffer2)(primeScreen, pDraw, attachment, format); + buffer = (*ds->CreateBuffer2)(GetScreenPrime(pDraw->pScreen, + DRI2GetDrawable(pDraw)->prime_id), + pDraw, attachment, format); else buffer = (*ds->CreateBuffer)(pDraw, attachment, format); return buffer; @@ -475,7 +472,7 @@ allocate_or_reuse_buffer(DrawablePtr pDraw, DRI2ScreenPtr ds, if ((old_buf < 0) || attachment == DRI2BufferFrontLeft || !dimensions_match || (pPriv->buffers[old_buf]->format != format)) { - *buffer = create_buffer (pDraw, attachment, format); + *buffer = create_buffer(ds, pDraw, attachment, format); return TRUE; } @@ -538,7 +535,7 @@ do_get_buffers(DrawablePtr pDraw, int *width, int *height, return NULL; } - ds = DRI2GetScreen(pDraw->pScreen); + ds = DRI2GetScreenPrime(pDraw->pScreen, pPriv->prime_id); dimensions_match = (pDraw->width == pPriv->width) && (pDraw->height == pPriv->height); @@ -1382,6 +1379,21 @@ DRI2ConfigNotify(WindowPtr pWin, int x, int y, int w, int h, int bw, return Success; } +static void +DRI2SetWindowPixmap(WindowPtr pWin, PixmapPtr pPix) +{ + DrawablePtr pDraw = (DrawablePtr) pWin; + ScreenPtr pScreen = pDraw->pScreen; + DRI2ScreenPtr ds = DRI2GetScreen(pScreen); + + pScreen->SetWindowPixmap = ds->SetWindowPixmap; + (*pScreen->SetWindowPixmap) (pWin, pPix); + ds->SetWindowPixmap = pScreen->SetWindowPixmap; + pScreen->SetWindowPixmap = DRI2SetWindowPixmap; + + DRI2InvalidateDrawableAll(pDraw); +} + #define MAX_PRIME DRI2DriverPrimeMask static int get_prime_id(void) @@ -1528,6 +1540,9 @@ DRI2ScreenInit(ScreenPtr pScreen, DRI2InfoPtr info) ds->ConfigNotify = pScreen->ConfigNotify; pScreen->ConfigNotify = DRI2ConfigNotify; + ds->SetWindowPixmap = pScreen->SetWindowPixmap; + pScreen->SetWindowPixmap = DRI2SetWindowPixmap; + xf86DrvMsg(pScreen->myNum, X_INFO, "[DRI2] Setup complete\n"); for (i = 0; i < sizeof(driverTypeNames) / sizeof(driverTypeNames[0]); i++) { if (i < ds->numDrivers && ds->driverNames[i]) { @@ -1552,6 +1567,7 @@ DRI2CloseScreen(ScreenPtr pScreen) DRI2ScreenPtr ds = DRI2GetScreen(pScreen); pScreen->ConfigNotify = ds->ConfigNotify; + pScreen->SetWindowPixmap = ds->SetWindowPixmap; if (ds->prime_id) prime_id_allocate_bitmask &= ~(1 << ds->prime_id); diff --git a/xorg-server/hw/xwayland/Makefile.am b/xorg-server/hw/xwayland/Makefile.am index 36e6127df..dc16b8bbe 100644 --- a/xorg-server/hw/xwayland/Makefile.am +++ b/xorg-server/hw/xwayland/Makefile.am @@ -1,10 +1,13 @@ bin_PROGRAMS = Xwayland Xwayland_CFLAGS = \ + -I$(top_srcdir)/glamor \ -I$(top_srcdir)/dri3 \ -DHAVE_DIX_CONFIG_H \ $(XWAYLANDMODULES_CFLAGS) \ - $(DIX_CFLAGS) + $(DIX_CFLAGS) \ + $(GLAMOR_CFLAGS) \ + $(GBM_CFLAGS) Xwayland_SOURCES = \ xwayland.c \ @@ -19,6 +22,7 @@ Xwayland_SOURCES = \ $(top_srcdir)/mi/miinitext.c Xwayland_LDADD = \ + $(glamor_lib) \ $(XWAYLAND_LIBS) \ $(XWAYLAND_SYS_LIBS) \ $(XSERVER_SYS_LIBS) @@ -26,5 +30,30 @@ Xwayland_DEPENDENCIES = $(XWAYLAND_LIBS) Xwayland_LDFLAGS = $(LD_EXPORT_SYMBOLS_FLAG) +if GLAMOR_EGL +Xwayland_SOURCES += xwayland-glamor.c + +nodist_Xwayland_SOURCES = \ + drm-client-protocol.h \ + drm-protocol.c + +CLEANFILES = $(nodist_Xwayland_SOURCES) + +EXTRA_DIST = drm.xml + +xwayland-glamor.c : $(nodist_Xwayland_SOURCES) + +glamor_lib = $(top_builddir)/glamor/libglamor.la + +Xwayland_LDADD += $(GLAMOR_LIBS) $(GBM_LIBS) -lEGL -lGL +endif + + relink: $(AM_V_at)rm -f Xwayland$(EXEEXT) && $(MAKE) Xwayland$(EXEEXT) + +%-protocol.c : %.xml + $(AM_V_GEN)$(WAYLAND_SCANNER) code < $< > $@ + +%-client-protocol.h : %.xml + $(AM_V_GEN)$(WAYLAND_SCANNER) client-header < $< > $@ diff --git a/xorg-server/hw/xwayland/drm.xml b/xorg-server/hw/xwayland/drm.xml new file mode 100644 index 000000000..8a3ad69b2 --- /dev/null +++ b/xorg-server/hw/xwayland/drm.xml @@ -0,0 +1,182 @@ +<?xml version="1.0" encoding="UTF-8"?> +<protocol name="drm"> + + <copyright> + Copyright © 2008-2011 Kristian Høgsberg + Copyright © 2010-2011 Intel Corporation + + Permission to use, copy, modify, distribute, and sell this + software and its documentation for any purpose is hereby granted + without fee, provided that\n the above copyright notice appear in + all copies and that both that copyright notice and this permission + notice appear in supporting documentation, and that the name of + the copyright holders not be used in advertising or publicity + pertaining to distribution of the software without specific, + written prior permission. The copyright holders make no + representations about the suitability of this software for any + purpose. It is provided "as is" without express or implied + warranty. + + THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS + SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND + FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY + SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN + AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, + ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF + THIS SOFTWARE. + </copyright> + + <!-- drm support. This object is created by the server and published + using the display's global event. --> + <interface name="wl_drm" version="2"> + <enum name="error"> + <entry name="authenticate_fail" value="0"/> + <entry name="invalid_format" value="1"/> + <entry name="invalid_name" value="2"/> + </enum> + + <enum name="format"> + <!-- The drm format codes match the #defines in drm_fourcc.h. + The formats actually supported by the compositor will be + reported by the format event. --> + <entry name="c8" value="0x20203843"/> + <entry name="rgb332" value="0x38424752"/> + <entry name="bgr233" value="0x38524742"/> + <entry name="xrgb4444" value="0x32315258"/> + <entry name="xbgr4444" value="0x32314258"/> + <entry name="rgbx4444" value="0x32315852"/> + <entry name="bgrx4444" value="0x32315842"/> + <entry name="argb4444" value="0x32315241"/> + <entry name="abgr4444" value="0x32314241"/> + <entry name="rgba4444" value="0x32314152"/> + <entry name="bgra4444" value="0x32314142"/> + <entry name="xrgb1555" value="0x35315258"/> + <entry name="xbgr1555" value="0x35314258"/> + <entry name="rgbx5551" value="0x35315852"/> + <entry name="bgrx5551" value="0x35315842"/> + <entry name="argb1555" value="0x35315241"/> + <entry name="abgr1555" value="0x35314241"/> + <entry name="rgba5551" value="0x35314152"/> + <entry name="bgra5551" value="0x35314142"/> + <entry name="rgb565" value="0x36314752"/> + <entry name="bgr565" value="0x36314742"/> + <entry name="rgb888" value="0x34324752"/> + <entry name="bgr888" value="0x34324742"/> + <entry name="xrgb8888" value="0x34325258"/> + <entry name="xbgr8888" value="0x34324258"/> + <entry name="rgbx8888" value="0x34325852"/> + <entry name="bgrx8888" value="0x34325842"/> + <entry name="argb8888" value="0x34325241"/> + <entry name="abgr8888" value="0x34324241"/> + <entry name="rgba8888" value="0x34324152"/> + <entry name="bgra8888" value="0x34324142"/> + <entry name="xrgb2101010" value="0x30335258"/> + <entry name="xbgr2101010" value="0x30334258"/> + <entry name="rgbx1010102" value="0x30335852"/> + <entry name="bgrx1010102" value="0x30335842"/> + <entry name="argb2101010" value="0x30335241"/> + <entry name="abgr2101010" value="0x30334241"/> + <entry name="rgba1010102" value="0x30334152"/> + <entry name="bgra1010102" value="0x30334142"/> + <entry name="yuyv" value="0x56595559"/> + <entry name="yvyu" value="0x55595659"/> + <entry name="uyvy" value="0x59565955"/> + <entry name="vyuy" value="0x59555956"/> + <entry name="ayuv" value="0x56555941"/> + <entry name="nv12" value="0x3231564e"/> + <entry name="nv21" value="0x3132564e"/> + <entry name="nv16" value="0x3631564e"/> + <entry name="nv61" value="0x3136564e"/> + <entry name="yuv410" value="0x39565559"/> + <entry name="yvu410" value="0x39555659"/> + <entry name="yuv411" value="0x31315559"/> + <entry name="yvu411" value="0x31315659"/> + <entry name="yuv420" value="0x32315559"/> + <entry name="yvu420" value="0x32315659"/> + <entry name="yuv422" value="0x36315559"/> + <entry name="yvu422" value="0x36315659"/> + <entry name="yuv444" value="0x34325559"/> + <entry name="yvu444" value="0x34325659"/> + </enum> + + <!-- Call this request with the magic received from drmGetMagic(). + It will be passed on to the drmAuthMagic() or + DRIAuthConnection() call. This authentication must be + completed before create_buffer could be used. --> + <request name="authenticate"> + <arg name="id" type="uint"/> + </request> + + <!-- Create a wayland buffer for the named DRM buffer. The DRM + surface must have a name using the flink ioctl --> + <request name="create_buffer"> + <arg name="id" type="new_id" interface="wl_buffer"/> + <arg name="name" type="uint"/> + <arg name="width" type="int"/> + <arg name="height" type="int"/> + <arg name="stride" type="uint"/> + <arg name="format" type="uint"/> + </request> + + <!-- Create a wayland buffer for the named DRM buffer. The DRM + surface must have a name using the flink ioctl --> + <request name="create_planar_buffer"> + <arg name="id" type="new_id" interface="wl_buffer"/> + <arg name="name" type="uint"/> + <arg name="width" type="int"/> + <arg name="height" type="int"/> + <arg name="format" type="uint"/> + <arg name="offset0" type="int"/> + <arg name="stride0" type="int"/> + <arg name="offset1" type="int"/> + <arg name="stride1" type="int"/> + <arg name="offset2" type="int"/> + <arg name="stride2" type="int"/> + </request> + + <!-- Create a wayland buffer for the prime fd. Use for regular and planar + buffers. Pass 0 for offset and stride for unused planes. --> + <request name="create_prime_buffer" since="2"> + <arg name="id" type="new_id" interface="wl_buffer"/> + <arg name="name" type="fd"/> + <arg name="width" type="int"/> + <arg name="height" type="int"/> + <arg name="format" type="uint"/> + <arg name="offset0" type="int"/> + <arg name="stride0" type="int"/> + <arg name="offset1" type="int"/> + <arg name="stride1" type="int"/> + <arg name="offset2" type="int"/> + <arg name="stride2" type="int"/> + </request> + + <!-- Notification of the path of the drm device which is used by + the server. The client should use this device for creating + local buffers. Only buffers created from this device should + be be passed to the server using this drm object's + create_buffer request. --> + <event name="device"> + <arg name="name" type="string"/> + </event> + + <event name="format"> + <arg name="format" type="uint"/> + </event> + + <!-- Raised if the authenticate request succeeded --> + <event name="authenticated"/> + + <enum name="capability" since="2"> + <description summary="wl_drm capability bitmask"> + Bitmask of capabilities. + </description> + <entry name="prime" value="1" summary="wl_drm prime available"/> + </enum> + + <event name="capabilities"> + <arg name="value" type="uint"/> + </event> + </interface> + +</protocol> diff --git a/xorg-server/hw/xwayland/xwayland-glamor.c b/xorg-server/hw/xwayland/xwayland-glamor.c new file mode 100644 index 000000000..4be883fa3 --- /dev/null +++ b/xorg-server/hw/xwayland/xwayland-glamor.c @@ -0,0 +1,570 @@ +/* + * Copyright © 2011-2014 Intel Corporation + * + * Permission to use, copy, modify, distribute, and sell this software + * and its documentation for any purpose is hereby granted without + * fee, provided that the above copyright notice appear in all copies + * and that both that copyright notice and this permission notice + * appear in supporting documentation, and that the name of the + * copyright holders not be used in advertising or publicity + * pertaining to distribution of the software without specific, + * written prior permission. The copyright holders make no + * representations about the suitability of this software for any + * purpose. It is provided "as is" without express or implied + * warranty. + * + * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS + * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND + * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY + * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN + * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING + * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS + * SOFTWARE. + */ + +#include "xwayland.h" + +#include <fcntl.h> +#include <sys/stat.h> +#include <xf86drm.h> + +#define MESA_EGL_NO_X11_HEADERS +#include <gbm.h> +#include <epoxy/egl.h> +#include <epoxy/gl.h> + +#include <glamor.h> +#include <glamor_context.h> +#include <dri3.h> +#include "drm-client-protocol.h" + +struct xwl_pixmap { + struct wl_buffer *buffer; + struct gbm_bo *bo; + void *image; + unsigned int texture; +}; + +static void +xwl_glamor_egl_make_current(struct glamor_context *glamor_ctx) +{ + eglMakeCurrent(glamor_ctx->display, EGL_NO_SURFACE, + EGL_NO_SURFACE, EGL_NO_CONTEXT); + if (!eglMakeCurrent(glamor_ctx->display, + EGL_NO_SURFACE, EGL_NO_SURFACE, + glamor_ctx->ctx)) + FatalError("Failed to make EGL context current\n"); +} + +static uint32_t +drm_format_for_depth(int depth) +{ + switch (depth) { + case 15: + return WL_DRM_FORMAT_XRGB1555; + case 16: + return WL_DRM_FORMAT_RGB565; + case 24: + return WL_DRM_FORMAT_XRGB8888; + default: + ErrorF("unexpected depth: %d\n", depth); + case 32: + return WL_DRM_FORMAT_ARGB8888; + } +} + +static uint32_t +gbm_format_for_depth(int depth) +{ + switch (depth) { + case 16: + return GBM_FORMAT_RGB565; + case 24: + return GBM_FORMAT_XRGB8888; + default: + ErrorF("unexpected depth: %d\n", depth); + case 32: + return GBM_FORMAT_ARGB8888; + } +} + +void +glamor_egl_screen_init(ScreenPtr screen, struct glamor_context *glamor_ctx) +{ + struct xwl_screen *xwl_screen = xwl_screen_get(screen); + + glamor_ctx->ctx = xwl_screen->egl_context; + glamor_ctx->display = xwl_screen->egl_display; + + glamor_ctx->make_current = xwl_glamor_egl_make_current; + + xwl_screen->glamor_ctx = glamor_ctx; +} + +static PixmapPtr +xwl_glamor_create_pixmap_for_bo(ScreenPtr screen, struct gbm_bo *bo, int depth) +{ + PixmapPtr pixmap; + struct xwl_pixmap *xwl_pixmap; + struct xwl_screen *xwl_screen = xwl_screen_get(screen); + + xwl_pixmap = malloc(sizeof *xwl_pixmap); + if (xwl_pixmap == NULL) + return NULL; + + pixmap = glamor_create_pixmap(screen, + gbm_bo_get_width(bo), + gbm_bo_get_height(bo), + depth, + GLAMOR_CREATE_PIXMAP_NO_TEXTURE); + if (pixmap == NULL) { + free(xwl_pixmap); + return NULL; + } + + if (lastGLContext != xwl_screen->glamor_ctx) { + lastGLContext = xwl_screen->glamor_ctx; + xwl_glamor_egl_make_current(xwl_screen->glamor_ctx); + } + + xwl_pixmap->bo = bo; + xwl_pixmap->buffer = NULL; + xwl_pixmap->image = eglCreateImageKHR(xwl_screen->egl_display, + xwl_screen->egl_context, + EGL_NATIVE_PIXMAP_KHR, + xwl_pixmap->bo, NULL); + + glGenTextures(1, &xwl_pixmap->texture); + glBindTexture(GL_TEXTURE_2D, xwl_pixmap->texture); + glEGLImageTargetTexture2DOES(GL_TEXTURE_2D, xwl_pixmap->image); + glBindTexture(GL_TEXTURE_2D, 0); + + xwl_pixmap_set_private(pixmap, xwl_pixmap); + + glamor_set_pixmap_texture(pixmap, xwl_pixmap->texture); + glamor_set_pixmap_type(pixmap, GLAMOR_TEXTURE_DRM); + + return pixmap; +} + +struct wl_buffer * +xwl_glamor_pixmap_get_wl_buffer(PixmapPtr pixmap) +{ + struct xwl_screen *xwl_screen = xwl_screen_get(pixmap->drawable.pScreen); + struct xwl_pixmap *xwl_pixmap = xwl_pixmap_get(pixmap); + int prime_fd; + + if (xwl_pixmap->buffer) + return xwl_pixmap->buffer; + + prime_fd = gbm_bo_get_fd(xwl_pixmap->bo); + if (prime_fd == -1) + return NULL; + + xwl_pixmap->buffer = + wl_drm_create_prime_buffer(xwl_screen->drm, prime_fd, + pixmap->drawable.width, + pixmap->drawable.height, + drm_format_for_depth(pixmap->drawable.depth), + 0, gbm_bo_get_stride(xwl_pixmap->bo), + 0, 0, + 0, 0); + + close(prime_fd); + + return xwl_pixmap->buffer; +} + +static PixmapPtr +xwl_glamor_create_pixmap(ScreenPtr screen, + int width, int height, int depth, unsigned int hint) +{ + struct xwl_screen *xwl_screen = xwl_screen_get(screen); + struct gbm_bo *bo; + + if (width > 0 && height > 0 && depth >= 15 && + (hint == 0 || + hint == CREATE_PIXMAP_USAGE_BACKING_PIXMAP || + hint == CREATE_PIXMAP_USAGE_SHARED)) { + bo = gbm_bo_create(xwl_screen->gbm, width, height, + gbm_format_for_depth(depth), + GBM_BO_USE_SCANOUT | GBM_BO_USE_RENDERING); + + if (bo) + return xwl_glamor_create_pixmap_for_bo(screen, bo, depth); + } + + return glamor_create_pixmap(screen, width, height, depth, hint); +} + +static Bool +xwl_glamor_destroy_pixmap(PixmapPtr pixmap) +{ + struct xwl_screen *xwl_screen = xwl_screen_get(pixmap->drawable.pScreen); + struct xwl_pixmap *xwl_pixmap = xwl_pixmap_get(pixmap); + + if (xwl_pixmap && pixmap->refcnt == 1) { + if (xwl_pixmap->buffer) + wl_buffer_destroy(xwl_pixmap->buffer); + + eglDestroyImageKHR(xwl_screen->egl_display, xwl_pixmap->image); + gbm_bo_destroy(xwl_pixmap->bo); + free(xwl_pixmap); + } + + return glamor_destroy_pixmap(pixmap); +} + +static Bool +xwl_glamor_create_screen_resources(ScreenPtr screen) +{ + struct xwl_screen *xwl_screen = xwl_screen_get(screen); + int ret; + + screen->CreateScreenResources = xwl_screen->CreateScreenResources; + ret = (*screen->CreateScreenResources) (screen); + xwl_screen->CreateScreenResources = screen->CreateScreenResources; + screen->CreateScreenResources = xwl_glamor_create_screen_resources; + + if (!ret) + return ret; + + if (xwl_screen->rootless) + screen->devPrivate = + fbCreatePixmap(screen, 0, 0, screen->rootDepth, 0); + else { + screen->devPrivate = + xwl_glamor_create_pixmap(screen, screen->width, screen->height, + screen->rootDepth, + CREATE_PIXMAP_USAGE_BACKING_PIXMAP); + if (screen->devPrivate) + glamor_set_screen_pixmap(screen->devPrivate, NULL); + } + + return screen->devPrivate != NULL; +} + +static char +is_fd_render_node(int fd) +{ + struct stat render; + + if (fstat(fd, &render)) + return 0; + if (!S_ISCHR(render.st_mode)) + return 0; + if (render.st_rdev & 0x80) + return 1; + + return 0; +} + +static void +xwl_drm_init_egl(struct xwl_screen *xwl_screen) +{ + EGLint major, minor; + const char *version; + + if (xwl_screen->egl_display) + return; + + xwl_screen->expecting_event--; + + xwl_screen->gbm = gbm_create_device(xwl_screen->drm_fd); + if (xwl_screen->gbm == NULL) { + ErrorF("couldn't get display device\n"); + return; + } + + xwl_screen->egl_display = eglGetDisplay(xwl_screen->gbm); + if (xwl_screen->egl_display == EGL_NO_DISPLAY) { + ErrorF("eglGetDisplay() failed\n"); + return; + } + + eglBindAPI(EGL_OPENGL_API); + if (!eglInitialize(xwl_screen->egl_display, &major, &minor)) { + ErrorF("eglInitialize() failed\n"); + return; + } + + version = eglQueryString(xwl_screen->egl_display, EGL_VERSION); + ErrorF("glamor: EGL version %s:\n", version); + + xwl_screen->egl_context = eglCreateContext(xwl_screen->egl_display, + NULL, EGL_NO_CONTEXT, NULL); + if (xwl_screen->egl_context == EGL_NO_CONTEXT) { + ErrorF("Failed to create EGL context\n"); + return; + } + + if (!eglMakeCurrent(xwl_screen->egl_display, + EGL_NO_SURFACE, EGL_NO_SURFACE, + xwl_screen->egl_context)) { + ErrorF("Failed to make EGL context current\n"); + return; + } + + if (!epoxy_has_gl_extension("GL_OES_EGL_image")) { + ErrorF("GL_OES_EGL_image no available"); + return; + } + + return; +} + +static void +xwl_drm_handle_device(void *data, struct wl_drm *drm, const char *device) +{ + struct xwl_screen *xwl_screen = data; + drm_magic_t magic; + + xwl_screen->device_name = strdup(device); + if (!xwl_screen->device_name) + return; + + xwl_screen->drm_fd = open(xwl_screen->device_name, O_RDWR | O_CLOEXEC); + if (xwl_screen->drm_fd == -1) { + ErrorF("wayland-egl: could not open %s (%s)", + xwl_screen->device_name, strerror(errno)); + return; + } + + if (is_fd_render_node(xwl_screen->drm_fd)) { + xwl_screen->fd_render_node = 1; + xwl_drm_init_egl(xwl_screen); + } else { + drmGetMagic(xwl_screen->drm_fd, &magic); + wl_drm_authenticate(xwl_screen->drm, magic); + } +} + +static void +xwl_drm_handle_format(void *data, struct wl_drm *drm, uint32_t format) +{ + struct xwl_screen *xwl_screen = data; + + switch (format) { + case WL_DRM_FORMAT_ARGB8888: + xwl_screen->formats |= XWL_FORMAT_ARGB8888; + break; + case WL_DRM_FORMAT_XRGB8888: + xwl_screen->formats |= XWL_FORMAT_XRGB8888; + break; + case WL_DRM_FORMAT_RGB565: + xwl_screen->formats |= XWL_FORMAT_RGB565; + break; + } +} + +static void +xwl_drm_handle_authenticated(void *data, struct wl_drm *drm) +{ + struct xwl_screen *xwl_screen = data; + + if (!xwl_screen->egl_display) + xwl_drm_init_egl(xwl_screen); +} + +static void +xwl_drm_handle_capabilities(void *data, struct wl_drm *drm, uint32_t value) +{ + struct xwl_screen *xwl_screen = data; + + xwl_screen->capabilities = value; +} + +static const struct wl_drm_listener xwl_drm_listener = { + xwl_drm_handle_device, + xwl_drm_handle_format, + xwl_drm_handle_authenticated, + xwl_drm_handle_capabilities +}; + +Bool +xwl_screen_init_glamor(struct xwl_screen *xwl_screen, + uint32_t id, uint32_t version) +{ + if (version < 2) + return FALSE; + + xwl_screen->drm = + wl_registry_bind(xwl_screen->registry, id, &wl_drm_interface, 2); + wl_drm_add_listener(xwl_screen->drm, &xwl_drm_listener, xwl_screen); + xwl_screen->expecting_event++; + + return TRUE; +} + +void +glamor_egl_destroy_textured_pixmap(PixmapPtr pixmap) +{ + glamor_destroy_textured_pixmap(pixmap); +} + +int +glamor_egl_dri3_fd_name_from_tex(ScreenPtr screen, + PixmapPtr pixmap, + unsigned int tex, + Bool want_name, CARD16 *stride, CARD32 *size) +{ + return 0; +} + +unsigned int +glamor_egl_create_argb8888_based_texture(ScreenPtr screen, int w, int h) +{ + return 0; +} + +struct xwl_auth_state { + int fd; + ClientPtr client; +}; + +static void +sync_callback(void *data, struct wl_callback *callback, uint32_t serial) +{ + struct xwl_auth_state *state = data; + + dri3_send_open_reply(state->client, state->fd); + AttendClient(state->client); + free(state); + wl_callback_destroy(callback); +} + +static const struct wl_callback_listener sync_listener = { + sync_callback +}; + +static int +xwl_dri3_open_client(ClientPtr client, + ScreenPtr screen, + RRProviderPtr provider, + int *pfd) +{ + struct xwl_screen *xwl_screen = xwl_screen_get(screen); + struct xwl_auth_state *state; + struct wl_callback *callback; + drm_magic_t magic; + int fd; + + fd = open(xwl_screen->device_name, O_RDWR | O_CLOEXEC); + if (fd < 0) + return BadAlloc; + if (xwl_screen->fd_render_node) { + *pfd = fd; + return Success; + } + + state = malloc(sizeof *state); + if (state == NULL) { + close(fd); + return BadAlloc; + } + + state->client = client; + state->fd = fd; + + if (drmGetMagic(state->fd, &magic) < 0) { + close(state->fd); + free(state); + return BadMatch; + } + + wl_drm_authenticate(xwl_screen->drm, magic); + callback = wl_display_sync(xwl_screen->display); + wl_callback_add_listener(callback, &sync_listener, state); + + IgnoreClient(client); + + return Success; +} + +static PixmapPtr +xwl_dri3_pixmap_from_fd(ScreenPtr screen, int fd, + CARD16 width, CARD16 height, CARD16 stride, + CARD8 depth, CARD8 bpp) +{ + struct xwl_screen *xwl_screen = xwl_screen_get(screen); + struct gbm_import_fd_data data; + struct gbm_bo *bo; + PixmapPtr pixmap; + + if (width == 0 || height == 0 || + depth < 15 || bpp != BitsPerPixel(depth) || stride < width * bpp / 8) + return NULL; + + data.fd = fd; + data.width = width; + data.height = height; + data.stride = stride; + data.format = gbm_format_for_depth(depth); + bo = gbm_bo_import(xwl_screen->gbm, GBM_BO_IMPORT_FD, &data, + GBM_BO_USE_SCANOUT | GBM_BO_USE_RENDERING); + if (bo == NULL) + return NULL; + + pixmap = xwl_glamor_create_pixmap_for_bo(screen, bo, depth); + if (pixmap == NULL) { + gbm_bo_destroy(bo); + return NULL; + } + + return pixmap; +} + +static int +xwl_dri3_fd_from_pixmap(ScreenPtr screen, PixmapPtr pixmap, + CARD16 *stride, CARD32 *size) +{ + struct xwl_pixmap *xwl_pixmap; + + xwl_pixmap = xwl_pixmap_get(pixmap); + + *stride = gbm_bo_get_stride(xwl_pixmap->bo); + *size = pixmap->drawable.width * *stride; + + return gbm_bo_get_fd(xwl_pixmap->bo); +} + +static dri3_screen_info_rec xwl_dri3_info = { + .version = 1, + .open = NULL, + .pixmap_from_fd = xwl_dri3_pixmap_from_fd, + .fd_from_pixmap = xwl_dri3_fd_from_pixmap, + .open_client = xwl_dri3_open_client, +}; + +Bool +xwl_glamor_init(struct xwl_screen *xwl_screen) +{ + ScreenPtr screen = xwl_screen->screen; + + if (xwl_screen->egl_context == EGL_NO_CONTEXT) { + ErrorF("Disabling glamor and dri3, EGL setup failed\n"); + return FALSE; + } + + if (!glamor_init(xwl_screen->screen, + GLAMOR_INVERTED_Y_AXIS | + GLAMOR_USE_EGL_SCREEN | + GLAMOR_USE_SCREEN | + GLAMOR_USE_PICTURE_SCREEN)) { + ErrorF("Failed to initialize glamor\n"); + return FALSE; + } + + if (!dri3_screen_init(xwl_screen->screen, &xwl_dri3_info)) { + ErrorF("Failed to initialize dri3\n"); + return FALSE; + } + + xwl_screen->CreateScreenResources = screen->CreateScreenResources; + screen->CreateScreenResources = xwl_glamor_create_screen_resources; + screen->CreatePixmap = xwl_glamor_create_pixmap; + screen->DestroyPixmap = xwl_glamor_destroy_pixmap; + + return TRUE; +} diff --git a/xorg-server/hw/xwayland/xwayland.c b/xorg-server/hw/xwayland/xwayland.c index b966e5070..17b7bf7fd 100644 --- a/xorg-server/hw/xwayland/xwayland.c +++ b/xorg-server/hw/xwayland/xwayland.c @@ -337,7 +337,13 @@ xwl_screen_post_damage(struct xwl_screen *xwl_screen) pixmap = (*xwl_screen->screen->GetWindowPixmap) (xwl_window->window); - buffer = xwl_shm_pixmap_get_wl_buffer(pixmap); +#if GLAMOR_HAS_GBM + if (xwl_screen->glamor) + buffer = xwl_glamor_pixmap_get_wl_buffer(pixmap); +#endif + if (!xwl_screen->glamor) + buffer = xwl_shm_pixmap_get_wl_buffer(pixmap); + wl_surface_attach(xwl_window->surface, buffer, 0, 0); for (i = 0; i < count; i++) { box = &RegionRects(region)[i]; @@ -373,6 +379,12 @@ registry_global(void *data, struct wl_registry *registry, uint32_t id, xwl_output_create(xwl_screen, id); xwl_screen->expecting_event++; } +#ifdef GLAMOR_HAS_GBM + else if (xwl_screen->glamor && + strcmp(interface, "wl_drm") == 0 && version >= 2) { + xwl_screen_init_glamor(xwl_screen, id, version); + } +#endif } static void @@ -495,6 +507,10 @@ xwl_screen_init(ScreenPtr pScreen, int argc, char **argv) dixSetPrivate(&pScreen->devPrivates, &xwl_screen_private_key, xwl_screen); xwl_screen->screen = pScreen; +#ifdef GLAMOR_HAS_GBM + xwl_screen->glamor = 1; +#endif + for (i = 1; i < argc; i++) { if (strcmp(argv[i], "-rootless") == 0) { xwl_screen->rootless = 1; @@ -514,6 +530,9 @@ xwl_screen_init(ScreenPtr pScreen, int argc, char **argv) atoi(argv[i + 1]); i++; } + else if (strcmp(argv[i], "-shm") == 0) { + xwl_screen->glamor = 0; + } } if (xwl_screen->listen_fd_count > 0) { @@ -591,10 +610,19 @@ xwl_screen_init(ScreenPtr pScreen, int argc, char **argv) if (!xwl_screen_init_cursor(xwl_screen)) return FALSE; - xwl_screen->CreateScreenResources = pScreen->CreateScreenResources; - pScreen->CreateScreenResources = xwl_shm_create_screen_resources; - pScreen->CreatePixmap = xwl_shm_create_pixmap; - pScreen->DestroyPixmap = xwl_shm_destroy_pixmap; +#ifdef GLAMOR_HAS_GBM + if (xwl_screen->glamor && !xwl_glamor_init(xwl_screen)) { + ErrorF("Failed to initialize glamor, falling back to sw\n"); + xwl_screen->glamor = 0; + } +#endif + + if (!xwl_screen->glamor) { + xwl_screen->CreateScreenResources = pScreen->CreateScreenResources; + pScreen->CreateScreenResources = xwl_shm_create_screen_resources; + pScreen->CreatePixmap = xwl_shm_create_pixmap; + pScreen->DestroyPixmap = xwl_shm_destroy_pixmap; + } xwl_screen->RealizeWindow = pScreen->RealizeWindow; pScreen->RealizeWindow = xwl_realize_window; diff --git a/xorg-server/hw/xwayland/xwayland.h b/xorg-server/hw/xwayland/xwayland.h index 8157e71ff..fc6855044 100644 --- a/xorg-server/hw/xwayland/xwayland.h +++ b/xorg-server/hw/xwayland/xwayland.h @@ -55,6 +55,7 @@ struct xwl_screen { int listen_fds[5]; int listen_fd_count; int rootless; + int glamor; CreateScreenResourcesProcPtr CreateScreenResources; CloseScreenProcPtr CloseScreen; @@ -83,6 +84,16 @@ struct xwl_screen { #define XWL_FORMAT_RGB565 (1 << 2) int prepare_read; + + char *device_name; + int drm_fd; + int fd_render_node; + struct wl_drm *drm; + uint32_t formats; + uint32_t capabilities; + void *egl_display, *egl_context; + struct gbm_device *gbm; + struct glamor_context *glamor_ctx; }; struct xwl_window { @@ -161,4 +172,10 @@ Bool xwl_shm_destroy_pixmap(PixmapPtr pixmap); struct wl_buffer *xwl_shm_pixmap_get_wl_buffer(PixmapPtr pixmap); +Bool xwl_glamor_init(struct xwl_screen *xwl_screen); + +Bool xwl_screen_init_glamor(struct xwl_screen *xwl_screen, + uint32_t id, uint32_t version); +struct wl_buffer *xwl_glamor_pixmap_get_wl_buffer(PixmapPtr pixmap); + #endif diff --git a/xorg-server/include/servermd.h b/xorg-server/include/servermd.h index b785e931d..fff6ed156 100755 --- a/xorg-server/include/servermd.h +++ b/xorg-server/include/servermd.h @@ -114,8 +114,13 @@ SOFTWARE. #if defined(__powerpc__) || defined(__ppc__) || defined(__ppc64__) -#define IMAGE_BYTE_ORDER MSBFirst -#define BITMAP_BIT_ORDER MSBFirst +#if defined(__LITTLE_ENDIAN__) +#define IMAGE_BYTE_ORDER LSBFirst +#define BITMAP_BIT_ORDER LSBFirst +#else +#define IMAGE_BYTE_ORDER MSBFirst +#define BITMAP_BIT_ORDER MSBFirst +#endif #define GLYPHPADBYTES 4 #endif /* PowerPC */ diff --git a/xorg-server/present/present.c b/xorg-server/present/present.c index fb511eb53..6528bd231 100644 --- a/xorg-server/present/present.c +++ b/xorg-server/present/present.c @@ -383,6 +383,24 @@ present_set_tree_pixmap(WindowPtr window, PixmapPtr pixmap) } static void +present_set_abort_flip(ScreenPtr screen) +{ + present_screen_priv_ptr screen_priv = present_screen_priv(screen); + + /* Switch back to using the screen pixmap now to avoid + * 2D applications drawing to the wrong pixmap. + */ + + if (screen_priv->flip_window) + present_set_tree_pixmap(screen_priv->flip_window, + (*screen->GetScreenPixmap)(screen)); + + present_set_tree_pixmap(screen->root, (*screen->GetScreenPixmap)(screen)); + + screen_priv->flip_pending->abort_flip = TRUE; +} + +static void present_unflip(ScreenPtr screen) { present_screen_priv_ptr screen_priv = present_screen_priv(screen); @@ -511,7 +529,7 @@ present_check_flip_window (WindowPtr window) if (flip_pending->window == window) { if (!present_check_flip(flip_pending->crtc, window, flip_pending->pixmap, flip_pending->sync_flip, NULL, 0, 0)) - flip_pending->abort_flip = TRUE; + present_set_abort_flip(screen); } } else { /* @@ -578,6 +596,7 @@ present_execute(present_vblank_ptr vblank, uint64_t ust, uint64_t crtc_msc) } xorg_list_del(&vblank->event_queue); + xorg_list_del(&vblank->window_list); vblank->queued = FALSE; if (vblank->pixmap && vblank->window) { @@ -633,7 +652,7 @@ present_execute(present_vblank_ptr vblank, uint64_t ust, uint64_t crtc_msc) /* Check pending flip */ if (window == screen_priv->flip_pending->window) - screen_priv->flip_pending->abort_flip = TRUE; + present_set_abort_flip(screen); } else if (!screen_priv->unflip_event_id) { /* Check current flip @@ -752,7 +771,7 @@ present_pixmap(WindowPtr window, if (!vblank->queued) continue; - if (vblank->crtc != target_crtc || vblank->target_msc > target_msc) + if (vblank->crtc != target_crtc || vblank->target_msc != target_msc) continue; DebugPresent(("\tx %lld %p %8lld: %08lx -> %08lx (crtc %p)\n", @@ -915,7 +934,7 @@ present_flip_destroy(ScreenPtr screen) /* Do the actual cleanup once the flip has been performed by the hardware */ if (screen_priv->flip_pending) - screen_priv->flip_pending->abort_flip = TRUE; + present_set_abort_flip(screen); } void diff --git a/xorg-server/xkeyboard-config/rules/base.xml.in b/xorg-server/xkeyboard-config/rules/base.xml.in index 0b0c1482c..319878fab 100644 --- a/xorg-server/xkeyboard-config/rules/base.xml.in +++ b/xorg-server/xkeyboard-config/rules/base.xml.in @@ -794,7 +794,7 @@ <model> <configItem> <name>microsoft4000</name> - <_description>Microsoft Natural Wireless Ergonomic Keyboard 4000</_description> + <_description>Microsoft Natural Ergonomic Keyboard 4000</_description> <vendor>Microsoft Inc.</vendor> </configItem> </model> diff --git a/xorg-server/xkeyboard-config/symbols/apl b/xorg-server/xkeyboard-config/symbols/apl index 0800b5bbd..c60f11723 100644 --- a/xorg-server/xkeyboard-config/symbols/apl +++ b/xorg-server/xkeyboard-config/symbols/apl @@ -5,7 +5,7 @@ // This file supports: // - The Sharp APL for Unix (SAX) layout // - The IBM APL2 layout -// - The Manugistics APL*PLUS II layout (version 5.1, 1993) +// - The Manugistics APL*PLUS II (Version 5.1, 1993) keyboard layout // - The Dyalog APL layout - with additions for box drawing and commands // Unicode APL table: http://aplwiki.com/UnicodeAplTable @@ -16,33 +16,33 @@ // This file doesn't deal with all the combining stuff -- I'm not an APL programmer, // and am not quite sure what's needed here. However, it may be possible to get this -// working with dead keys and the like. Patches gratefully accepted. +// working with dead keys and the like. Patches gratefully accepted. // Some of the shift-key assignments may differ from the APL tradition. If -// that's not considered acceptable, it should be possible to remap the +// that's not considered acceptable, it should be possible to remap the // shift keys. I have striven, however, to ensure that the use of shift keys -// in these maps is at least self-consistent. +// in these maps is at least self-consistent. -// I'm assuming that this will be used with another keyboard layout (i.e. for -// your language), with a special shift key to use these maps. +// I'm assuming that this will be used with another keyboard layout (ie. for +// your language), with a special shift key to use these maps. -// 2011-12-22 Geoff Streeter <geoff@dyalog.com>, -// added the Dyalog support; -// corrected (what he thinks) are some errors: -// resolving the confusion between APL's and Unicode's concept of Left and Right tacks; -// unsure about some of the inheritance from APL2 into APLPLUS -- patches welcome; -// complied with freedesktop.org requirement that the keycodes be in sorted order, -// which leads to the bottom to top (roughly) definitions. +// 2012-09-26 changed "overbar" to macron which fixed some strangeness in xterm -// The default layout still has to be the first one. Choosing the basic Dyalog layout is -// definitely better than using the "common" one. Choosing the complete Dyalog layout is -// not useful to non-Dyalog users. +// 2011-12-22 Geoff Streeter: geoff@dyalog.com +// Added the Dyalog support. +// Corrected (what he thinks) are some errors. +// Resolving the confusion between APL's and Unicode's concept of Left and Right tacks. +// Unsure about some of the inheritance from APL2 into APLPLUS. Patches welcome. +// Complied with freedesktop.org requirement that the keycodes be in sorted order. Which +// leads to the bottom to top (roughly) definitions. -default partial alphanumeric_keys +// default layout seems to have to be the first one. Choosing the basic Dyalog layout is definitely +// better than using the "common" one. Choosing the complete Dyalog layout is not useful to non-Dyalog +// users. + +default partial alphanumeric_keys xkb_symbols "basic" { include "apl(dyalog_base)" // forward reference good APL keyboard without Dyalogs extras - - name[Group1]= "APL keyboard symbols"; }; // ┌─────┬─────┬─────┬─────┬─────┬─────┬─────┬─────┬─────┬─────┬─────┬─────┬─────┲━━━━━━━━━┓ @@ -64,6 +64,7 @@ xkb_symbols "basic" { partial hidden alphanumeric_keys xkb_symbols "common" { + name[Group1]= "APL"; key <AB01> { [ U2282 ] }; // Z: ⊂ -- Subset Of key <AB02> { [ U2283 ] }; // X: ⊃ -- Superset Of @@ -96,7 +97,7 @@ xkb_symbols "common" { key <AD11> { [ U2190 ] }; // [: ← -- Leftwards Arrow key <AE01> { [ diaeresis ] }; - key <AE02> { [ U00AF ] }; // ¯ -- Macron + key <AE02> { [ macron ] }; // ¯ -- Macron key <AE03> { [ less ] }; key <AE04> { [ U2264 ] }; // ≤ -- Less-than Or Equal To key <AE05> { [ equal ] }; @@ -128,7 +129,7 @@ xkb_symbols "common" { partial alphanumeric_keys xkb_symbols "unified" { - name[Group1]= "APL keyboard symbols (unified)"; + name[Group1]= "APL Keyboard Symbols: Unified Layout"; include "apl(common)" @@ -161,7 +162,7 @@ xkb_symbols "unified" { partial alphanumeric_keys xkb_symbols "sax" { - name[Group1]= "APL keyboard symbols (sax)"; + name[Group1]= "APL Keyboard Symbols"; include "apl(unified)" @@ -223,7 +224,7 @@ xkb_symbols "sax" { partial alphanumeric_keys xkb_symbols "apl2" { - name[Group1]= "APL keyboard symbols (IBM APL2)"; + name[Group1]= "APL Keyboard Symbols: IBM APL2"; include "apl(common)" @@ -235,7 +236,7 @@ xkb_symbols "apl2" { key <AB10> { [ slash, backslash, U233F ] }; // /: ⌿ -- AFS Slash Bar key <AC10> { [ bracketleft, parenleft, U234E ] }; // ;: ⍎ -- [See B key in SAX layout] - key <AC11> { [ bracketright, parenright, U2355 ] }; // ': ⍕ -- [See N key in SAX layout] + key <AC11> { [ bracketright, parenright, U2355 ] }; // ': ⍕ -- [See N key in SAX layout] key <AD11> { [ NoSymbol, U2192, U235E ] }; // [: (←) → ⍞ -- Rightwards Arrow / AFS Quote Quad key <AD12> { [ U2337, U2378, U2359 ] }; // ]: ⌷ ⍸ ⍙ -- AFS Squish Quad / AFS Iota Underbar / AFS Delta Underbar @@ -255,7 +256,7 @@ xkb_symbols "apl2" { key <BKSL> { [ U2261, U2377, U2364 ] }; // \: ≡ ⍷ ⍤ -- Identical To / AFS Epsilon Underbar / AFS Jot Diaeresis - key <TLDE> { [ NoSymbol, U233B, U2342 ] }; // `: ⌻ ⍂ -- + key <TLDE> { [ NoSymbol, U233B, U2342 ] }; // `: ⌻ ⍂ -- include "level3(ralt_switch)" }; @@ -283,13 +284,13 @@ xkb_symbols "apl2" { partial alphanumeric_keys xkb_symbols "aplplusII" { + name[Group1]= "APL Keyboard Symbols: Manugistics APL*PLUS II"; // AFS - short for APL Functional Symbol include "apl(apl2)" - name[Group1]= "APL keyboard symbols (Manugistics APL*PLUS II)"; key <AC10> { [ bracketleft, parenleft, U234E ] }; // ;: ⍎ -- [See B key in SAX layout] - key <AC11> { [ bracketright, parenright, U2355 ] }; // ': ⍕ -- [See N key in SAX layout] + key <AC11> { [ bracketright, parenright, U2355 ] }; // ': ⍕ -- [See N key in SAX layout] key <AD11> { [ U2190, NoSymbol, U235E ] }; // [: ← ⍞ -- Leftwards Arrow / AFS Quote Quad key <AD12> { [ U2192, NoSymbol, U236C ] }; // ]: → ⍬ -- Rightwards Arrow / AFS Zilde key <AE01> { [ NoSymbol, NoSymbol, U2261 ] }; // 1: ≡ -- Identical To @@ -320,9 +321,9 @@ xkb_symbols "aplplusII" { partial alphanumeric_keys xkb_symbols "aplx" { - include "apl(unified)" + name[Group1]= "APL Keyboard Symbols: APLX Unified APL Layout"; - name[Group1]= "APL keyboard symbols (APLX unified)"; + include "apl(unified)" key <AB08> { [ U235D, U236A ] }; // ,: ⍝ ⍪ -- APL Functional Symbol Up Shoe Jot / APL Functional Symbol Comma Bar key <AB09> { [ U2340, U2364 ] }; // .: ⍀ ⍤ -- APL Functional Symbol Backslash Bar / APL Functional Symbol Jot Diaeresis @@ -350,44 +351,57 @@ xkb_symbols "aplx" { }; // APL language support for the Dyalog keyboard. -// Dyalog Ltd sells this keyboard with APL engravings. The current model is -// engraved on a Cherry G80. Base languages for US, UK and DK are available. +// Dyalog Ltd sell this keyboard with APL engravings. The current model is +// engraved on a Cherry G80. Base languages for US, UK and DK are availible. -// Geoff Streeter, Dyalog Ltd. 2007-09-03 <geoff@dyalog.com> +// Geoff Streeter, Dyalog Ltd. 2007-09-03 +// geoff@dyalog.com // extended for APL special actions 2008-09-09 -// added a variant 2010-11-26 - -// The intention is that this keyboard layout overlays a base keyboard that provides +// add variant 2010-11-26 +// made BKSL and LTGT keys the same to remove a compatibility issue with the UK physical keyboard +// add key (quad equals) 2013-03-12 +// add currency 2014-05-23 +// add parallel 2014-05-23 +// add circle jot 2014-05-23 +// add t diaeresis 2014-05-23 +// add del diaerisis 2014-05-23 +// add quad query 2014-05-23 +// add dagger 2014-05-23 + +// The intention is that this keyboard layout overlays a base keyboard that provides // the alphabet and similar. If this keyboard is placed as the 2nd layout then it can // be reached with a latching shift to increase group by one. -partial hidden alphanumeric_keys +partial alphanumeric_keys xkb_symbols "dyalog_base" { + name[Group1]="APL"; + // ┌─────┬─────┬─────┬─────┬─────┬─────┬─────┬─────┬─────┬─────┬─────┬─────┬─────┲━━━━━━━━━┓ -// │ │ ⌶ │ ⍫ │ ⍒ │ ⍋ │ ⌽ │ ⍉ │ ⊖ │ ⍟ │ ⍱ │ ⍲ │ ! │ ⌹ ┃ ┃ +// │ ¤ │ ⌶ │ ⍫ │ ⍒ │ ⍋ │ ⌽ │ ⍉ │ ⊖ │ ⍟ │ ⍱ │ ⍲ │ ! │ ⌹ ┃ ┃ // │ ⋄ │ ¨ │ ¯ │ < │ ≤ │ = │ ≥ │ > │ ≠ │ ∨ │ ∧ │ × │ ÷ ┃ ┃ // ┢━━━━━┷━┱───┴─┬───┴─┬───┴─┬───┴─┬───┴─┬───┴─┬───┴─┬───┴─┬───┴─┬───┴─┬───┴─┬───┺━┳━━━━━━━┫ -// ┃ ┃ │ │ ⍷ │ │ ⍨ │ │ │ ⍸ │ ⍥ │ ⍣ │ ⍞ │ ⍬ ┃ ┃ +// ┃ ┃ ⍰ │ │ ⍷ │ ⌾ │ ⍨ │ │ │ ⍸ │ ⍥ │ ⍣ │ ⍞ │ ⍬ ┃ ┃ // ┃ ┃ ? │ ⍵ │ ∊ │ ⍴ │ ~ │ ↑ │ ↓ │ ⍳ │ ○ │ * │ ← │ → ┃ ┃ // ┣━━━━━━━┻┱────┴┬────┴┬────┴┬────┴┬────┴┬────┴┬────┴┬────┴┬────┴┬────┴┬────┴┬────┺┓ ┃ -// ┃ ┃ │ │ │ │ │ │ ⍤ │ │ ⌷ │ ≡ │ ≢ │ ⊣ ┃ ┃ +// ┃ ┃ │ │ │ │ ⍢ │ │ ⍤ │ ⌸ │ ⌷ │ ≡ │ ≢ │ ⊣ ┃ ┃ // ┃ ┃ ⍺ │ ⌈ │ ⌊ │ _ │ ∇ │ ∆ │ ∘ │ ' │ ⎕ │ ⍎ │ ⍕ │ ⊢ ┃ ┃ // ┣━━━━━━━┳┹────┬┴────┬┴────┬┴────┬┴────┬┴────┬┴────┬┴────┬┴────┬┴────┬┴────┲┷━━━━━┻━━━━━━┫ -// ┃ ┃ │ │ │ │ │ │ │ │ ⍪ │ ⍙ │ ⍠ ┃ ┃ +// ┃ ┃ │ │ │ │ │ ⍭ │ ⍡ │ ∥ │ ⍪ │ ⍙ │ ⍠ ┃ ┃ // ┃ ┃ │ ⊂ │ ⊃ │ ∩ │ ∪ │ ⊥ │ ⊤ │ | │ ⍝ │ ⍀ │ ⌿ ┃ ┃ // ┣━━━━━━━╋━━━━━┷━┳━━━┷━━━┱─┴─────┴─────┴─────┴─────┴─────┴───┲━┷━━━━━╈━━━━━┻━┳━━━━━━━┳━━━┛ // ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ // ┃ ┃ ┃ ┃ ┃ ┃ ┃ ┃ // ┗━━━━━━━┻━━━━━━━┻━━━━━━━┹───────────────────────────────────┺━━━━━━━┻━━━━━━━┻━━━━━━━┛ + key <AB01> { [ U2282 ] }; // subset of key <AB02> { [ U2283 ] }; // superset of key <AB03> { [ U2229 ] }; // intersection key <AB04> { [ U222A ] }; // union - key <AB05> { [ U22a5 ] }; // up tack - key <AB06> { [ U22a4 ] }; // down tack - key <AB07> { [ U007c ] }; // vertical line + key <AB05> { [ U22a5, U236d ] }; // up tack, stile tide + key <AB06> { [ U22a4, U2361 ] }; // down tack, down tack diaeresis + key <AB07> { [ bar, U2225 ] }; // vertical line, parallel to key <AB08> { [ U235d, U236a ] }; // up shoe jot, comma bar key <AB09> { [ U2340, U2359 ] }; // backslash bar, delta underbar key <AB10> { [ U233f, U2360 ] }; // slash bar, quad colon @@ -395,17 +409,17 @@ xkb_symbols "dyalog_base" { key <AC02> { [ U2308 ] }; // left ceiling key <AC03> { [ U230a ] }; // left floor key <AC04> { [ underscore ] }; // low line - key <AC05> { [ U2207 ] }; // nabla + key <AC05> { [ U2207, U2362 ] }; // nabla, del diaerisis key <AC06> { [ U2206 ] }; // increment key <AC07> { [ U2218, U2364 ] }; // ring operator, jot diaeresis - key <AC08> { [ apostrophe ] }; + key <AC08> { [ apostrophe, U2338 ] }; // quote, key key <AC09> { [ U2395, U2337 ] }; // quad, squish quad key <AC10> { [ U234e, U2261 ] }; // up tack jot, identical to key <AC11> { [ U2355, U2262 ] }; // down tack jot, not identical to - key <AD01> { [ question ] }; + key <AD01> { [ question, U2370 ] }; // ?, quad question key <AD02> { [ U2375 ] }; // omega key <AD03> { [ U220a, U2377 ] }; // small element of, epsilon underbar - key <AD04> { [ U2374 ] }; // rho + key <AD04> { [ U2374, U233E ] }; // rho, circle jot key <AD05> { [ asciitilde, U2368 ] }; // tilde, tilde diaeresis key <AD06> { [ U2191 ] }; // upwards arrow key <AD07> { [ U2193 ] }; // downwards arrow @@ -415,7 +429,7 @@ xkb_symbols "dyalog_base" { key <AD11> { [ U2190, U235e ] }; // left arrow, quote quad key <AD12> { [ U2192, U236c ] }; // right arrow, zilde key <AE01> { [ diaeresis, U2336 ] }; // i-beam - key <AE02> { [ overbar, U236B ] }; // deltilde + key <AE02> { [ macron, U236B ] }; // deltilde key <AE03> { [ less, U2352 ] }; // downgrade key <AE04> { [ U2264, U234b ] }; // lesseq upgrade key <AE05> { [ equal, U233d ] }; // circlestile @@ -425,13 +439,15 @@ xkb_symbols "dyalog_base" { key <AE09> { [ U2228, U2371 ] }; // logical or, down caret tilde key <AE10> { [ U2227, U2372 ] }; // logical and, up caret tilde key <AE11> { [ multiply, exclam ] }; - key <AE12> { [ division, U2339 ] }; // quad divide + key <AE12> { [ division, U2339 ] }; // quad divide key <BKSL> { [ U22a2, U22a3 ] }; // right tack, left tack - key <TLDE> { [ U22c4 ] }; // diamond + key <LTGT> { [ U22a2, U22a3 ] }; // right tack, left tack + key <TLDE> { [ U22c4, currency] }; // diamond }; -partial hidden keypad_keys +partial keypad_keys xkb_symbols "dyalog_box" { + name[Group1]="Dyalog box"; // ┌───┬───┬───┬───┐ // │ │ │ │ │ @@ -449,22 +465,22 @@ xkb_symbols "dyalog_box" { key <KP1> { [ U2514 ] }; // box drawing light up and right key <KP2> { [ U2534 ] }; // box drawing light up and horizontal key <KP3> { [ U2518 ] }; // box drawing light up and left - key <KP4> { [ U251c ] }; // box drawing light veritcal and right - key <KP5> { [ U253c ] }; // box drawing light veritcal and horizontal - key <KP6> { [ U2524 ] }; // box drawing light veritcal and left + key <KP4> { [ U251c ] }; // box drawing light vertical and right + key <KP5> { [ U253c ] }; // box drawing light vertical and horizontal + key <KP6> { [ U2524 ] }; // box drawing light vertical and left key <KP7> { [ U250c ] }; // box drawing light down and right key <KP8> { [ U252c ] }; // box drawing light down and horizontal key <KP9> { [ U2510 ] }; // box drawing light down and left key <KPDL> { [ U2502 ] }; // box drawing light vertical -}; +}; -partial hidden xkb_symbols "dyalog_codes" { + name[Group1]="Dyalog Codes"; // Layout of private use area for this. In the style of the Unicode book // -// APL special actions F800-F88F +// APL special actions F800-F88F // // │F800 F810 F820 F830 F840 F850 F860 F870 F880 // ├────┬────┬────┬────┬────┬────┬────┬────┬────┐ @@ -501,7 +517,7 @@ xkb_symbols "dyalog_codes" { // F│RL │FD │HK │Lc │BH │PU │ │ │OS │ // └────┴────┴────┴────┴────┴────┴────┴────┴────┘ // -// APL Function Keys F700-F7FF +// APL Function Keys F700-F7FF // // │F700 ... ... F7F0 // ├────┬────┬────┬────┬....┬────┬────┬────┬────┐ @@ -511,9 +527,9 @@ xkb_symbols "dyalog_codes" { // . // F│F15 │F31 │F47 │F63 │ │F207│F223│F239│F255│ // └────┴────┴────┴────┴....┴────┴────┴────┴────┘ -// +// // whilst these locations are defined. Dyalog's "aplkeys/xterm" file copes with -// normal function keys from the base keyboard rather than this overlay. +// normal function keys from the base keyboard rather than this overlay // ┌─────┐ ┌───┐ // │ │ │ZM │ @@ -537,6 +553,7 @@ xkb_symbols "dyalog_codes" { // ┃ ┃ ┃ ┃ TO ┃ ┃ ┃ ┃ // ┗━━━━━━━┻━━━━━━━┻━━━━━━━┹───────────────────────────────────┺━━━━━━━┻━━━━━━━┻━━━━━━━┛ + key <BKSP> { [ Uf850, Uf855 ] }; // BP CB key <ESC> { [ Uf800 ] }; // QT key <FK11> { [ Uf821, Uf821 ] }; // ZM, ZM put this on both, the unshifted one sometimes gets lost @@ -557,6 +574,7 @@ xkb_symbols "dyalog_codes" { key <RGHT> { [ Uf824, Uf854 ] }; // NX, RM key <UP> { [ Uf820 ] }; // BK + // ┌───┬───┬───┐ // │PT │LL │UL │ // │CP │LS │US │ @@ -584,6 +602,7 @@ xkb_symbols "dyalog_codes" { // │ │ │ │ // └───────┴───┴───┘ + key <KPAD> { [ Uf859 ] }; // TL key <KPDV> { [ Uf819 ] }; // RD key <KPMU> { [ Uf81a ] }; // TG @@ -594,5 +613,6 @@ xkb_symbols "dyalog" { include "apl(dyalog_base)" include "apl(dyalog_box)" include "apl(dyalog_codes)" - name[Group1] = "APL keyboard symbols (Dyalog)"; + name[Group1] = "Dyalog APL complete"; }; + diff --git a/xorg-server/xkeyboard-config/symbols/fr b/xorg-server/xkeyboard-config/symbols/fr index 3898b1c57..6658da4b5 100644 --- a/xorg-server/xkeyboard-config/symbols/fr +++ b/xorg-server/xkeyboard-config/symbols/fr @@ -128,7 +128,6 @@ xkb_symbols "oss" { include "latin" include "level3(ralt_switch)" include "nbsp(level4n)" - include "level5(rctrl_switch)" include "keypad(oss)" name[Group1]="French (alternative)"; diff --git a/xorg-server/xkeyboard-config/symbols/inet b/xorg-server/xkeyboard-config/symbols/inet index f7ccc6f81..613488f05 100644 --- a/xorg-server/xkeyboard-config/symbols/inet +++ b/xorg-server/xkeyboard-config/symbols/inet @@ -1271,7 +1271,7 @@ xkb_symbols "mx2750" { // Microsoft -// Microsoft Natural Wireless Ergonomic Keyboard 4000 +// Microsoft Natural Ergonomic Keyboard 4000 partial alphanumeric_keys xkb_symbols "microsoft4000" { include "inet(media_nav_common)" |