Merge "platform: msm_shared: Fixed device boot to fastboot after emergency dload"
diff --git a/app/aboot/aboot.c b/app/aboot/aboot.c
index 74e17e0..4f26616 100644
--- a/app/aboot/aboot.c
+++ b/app/aboot/aboot.c
@@ -132,6 +132,7 @@
/* make 4096 as default size to ensure EFS,EXT4's erasing */
#define DEFAULT_ERASE_SIZE 4096
#define MAX_PANEL_BUF_SIZE 196
+#define FOOTER_SIZE 16384
#define DISPLAY_DEFAULT_PREFIX "mdss_mdp"
#define BOOT_DEV_MAX_LEN 64
@@ -2501,6 +2502,7 @@
unsigned long long size = 0;
int index = INVALID_PTN;
uint8_t lun = 0;
+ char *footer = NULL;
#if VERIFIED_BOOT
if(!strcmp(arg, KEYSTORE_PTN_NAME))
@@ -2543,6 +2545,21 @@
fastboot_fail("failed to erase partition");
return;
}
+ /*Erase FDE metadata at the userdata footer*/
+ if(!(strncmp(arg, "userdata", 8)))
+ {
+ footer = memalign(CACHE_LINE, FOOTER_SIZE);
+ memset((void *)footer, 0, FOOTER_SIZE);
+
+ size = partition_get_size(index);
+
+ if (mmc_write((ptn + size) - FOOTER_SIZE , FOOTER_SIZE, (unsigned int *)footer)) {
+ fastboot_fail("failed to erase userdata footer");
+ free(footer);
+ return;
+ }
+ free(footer);
+ }
}
#if VERIFIED_BOOT
#if !VBOOT_MOTA
@@ -3166,6 +3183,7 @@
struct ptentry *ptn;
struct ptable *ptable;
unsigned extra = 0;
+ uint64_t partition_size = 0;
ptable = flash_get_ptable();
if (ptable == NULL) {
@@ -3197,6 +3215,17 @@
else
sz = ROUND_TO_PAGE(sz, page_mask);
+ partition_size = (uint64_t)ptn->length * (uint64_t)flash_num_pages_per_blk() * (uint64_t)flash_page_size();
+ if (partition_size > UINT_MAX) {
+ fastboot_fail("Invalid partition size");
+ return;
+ }
+
+ if (sz > partition_size) {
+ fastboot_fail("Image size too large");
+ return;
+ }
+
dprintf(INFO, "writing %d bytes to '%s'\n", sz, ptn->name);
if (!memcmp((void *)data, UBI_MAGIC, UBI_MAGIC_SIZE)) {
if (flash_ubi_img(ptn, data, sz)) {
diff --git a/app/aboot/mdtp.c b/app/aboot/mdtp.c
index f02eae9..136fab5 100644
--- a/app/aboot/mdtp.c
+++ b/app/aboot/mdtp.c
@@ -40,6 +40,7 @@
#include <stdlib.h>
#include <boot_verifier.h>
#include <image_verify.h>
+#include <qtimer.h>
#include "scm.h"
#include "mdtp.h"
#include "mdtp_fs.h"
@@ -74,7 +75,6 @@
extern int check_aboot_addr_range_overlap(uintptr_t start, uint32_t size);
int scm_random(uint32_t * rbuf, uint32_t r_len);
-extern void mdelay(unsigned msecs);
void free_mdtp_image(void);
/********************************************************************************/
@@ -240,10 +240,10 @@
/* Validate a hash table calculated per block of a given partition */
static int verify_partition_block_hash(char *name,
- uint64_t size,
- uint32_t verify_num_blocks,
- DIP_hash_table_entry_t *hash_table,
- uint8_t *force_verify_block)
+ uint64_t size,
+ uint32_t verify_num_blocks,
+ DIP_hash_table_entry_t *hash_table,
+ uint8_t *force_verify_block)
{
unsigned char digest[HASH_LEN]={0};
unsigned long long ptn = 0;
@@ -334,14 +334,14 @@
/* Validate the partition parameters read from DIP */
static int validate_partition_params(uint64_t size,
- mdtp_fwlock_mode_t hash_mode,
- uint32_t verify_ratio)
+ mdtp_fwlock_mode_t hash_mode,
+ uint32_t verify_ratio)
{
if (size == 0 || size > (uint64_t)MDTP_FWLOCK_BLOCK_SIZE * (uint64_t)MAX_BLOCKS ||
- hash_mode > MDTP_FWLOCK_MODE_FILES || verify_ratio > 100)
+ hash_mode > MDTP_FWLOCK_MODE_FILES || verify_ratio > 100)
{
dprintf(CRITICAL, "mdtp: validate_partition_params: error, size=%llu, hash_mode=%d, verify_ratio=%d\n",
- size, hash_mode, verify_ratio);
+ size, hash_mode, verify_ratio);
return -1;
}
@@ -350,11 +350,11 @@
/* Verify a given partitinon */
static int verify_partition(char *name,
- uint64_t size,
- mdtp_fwlock_mode_t hash_mode,
- uint32_t verify_num_blocks,
- DIP_hash_table_entry_t *hash_table,
- uint8_t *force_verify_block)
+ uint64_t size,
+ mdtp_fwlock_mode_t hash_mode,
+ uint32_t verify_num_blocks,
+ DIP_hash_table_entry_t *hash_table,
+ uint8_t *force_verify_block)
{
if (hash_mode == MDTP_FWLOCK_MODE_SINGLE)
{
@@ -524,14 +524,14 @@
ptn = partition_get_offset(index);
if(ptn == 0) {
dprintf(CRITICAL, "ERROR: partition %s not found\n",
- ext_partition->partition == MDTP_PARTITION_BOOT ? "boot" : "recovery");
+ ext_partition->partition == MDTP_PARTITION_BOOT ? "boot" : "recovery");
return -1;
}
if(mmc_read(ptn + ext_partition->image_size, (void *)(ext_partition->image_addr + ext_partition->image_size), ext_partition->page_size))
{
dprintf(CRITICAL, "ERROR: Cannot read %s image signature\n",
- ext_partition->partition == MDTP_PARTITION_BOOT ? "boot" : "recovery");
+ ext_partition->partition == MDTP_PARTITION_BOOT ? "boot" : "recovery");
return -1;
}
}
@@ -570,8 +570,8 @@
/* Verify all protected partitinons according to the DIP */
static void verify_all_partitions(DIP_t *dip,
- mdtp_ext_partition_verification_t *ext_partition,
- verify_result_t *verify_result)
+ mdtp_ext_partition_verification_t *ext_partition,
+ verify_result_t *verify_result)
{
int i;
int verify_failure = 0;
@@ -810,8 +810,8 @@
arch_invalidate_cache_range((addr_t)dec_dip, sizeof(DIP_t));
ret = mdtp_cipher_dip_cmd((uint8_t*)enc_dip, sizeof(DIP_t),
- (uint8_t*)dec_dip, sizeof(DIP_t),
- DIP_DECRYPT);
+ (uint8_t*)dec_dip, sizeof(DIP_t),
+ DIP_DECRYPT);
if (ret)
{
dprintf(CRITICAL, "mdtp: mdtp_tzbsp_dec_verify_DIP: ERROR, cannot cipher DIP\n");
@@ -856,8 +856,8 @@
arch_invalidate_cache_range((addr_t)enc_dip, sizeof(DIP_t));
ret = mdtp_cipher_dip_cmd((uint8_t*)dec_dip, sizeof(DIP_t),
- (uint8_t*)enc_dip, sizeof(DIP_t),
- DIP_ENCRYPT);
+ (uint8_t*)enc_dip, sizeof(DIP_t),
+ DIP_ENCRYPT);
if (ret)
{
dprintf(CRITICAL, "mdtp: mdtp_tzbsp_enc_hash_DIP: ERROR, cannot cipher DIP\n");
@@ -886,11 +886,7 @@
/* Disallow the CIPHER_DIP SCM by calling it MAX_CIPHER_DIP_SCM_CALLS times */
for (i=0; i<MAX_CIPHER_DIP_SCM_CALLS; i++)
{
- if(mdtp_tzbsp_enc_hash_DIP(dip, dip) != 0)
- {
- /* Couldn't disallowd CIPHER_DIP SCM - stop device from booting */
- display_error_msg(); /* This will never return */
- }
+ mdtp_tzbsp_enc_hash_DIP(dip, dip);
}
free(dip);
@@ -947,7 +943,7 @@
//Bad size
if(validate_partition_params((uint64_t)MDTP_FWLOCK_BLOCK_SIZE * (uint64_t)MAX_BLOCKS + 1,
- MDTP_FWLOCK_MODE_SINGLE, 1) != -1){
+ MDTP_FWLOCK_MODE_SINGLE, 1) != -1){
dprintf(INFO, "validate_partition_params_ut: [FAIL (2)].\n");
return -1;
}
@@ -969,7 +965,7 @@
//Unkown hashing mode
if(verify_partition("system", partition_size, BAD_HASH_MODE, verify_num_blocks,
- &partition_hash_table, &partition_force_verify_block) != -1){
+ &partition_hash_table, &partition_force_verify_block) != -1){
dprintf(INFO, "verify_partition_ut: Failed Test 1.\n");
dprintf(INFO, "MDTP LK UT: verify_partition_ut [ FAIL ]\n");
return -1;
diff --git a/app/aboot/mdtp_fs.c b/app/aboot/mdtp_fs.c
index b848c7a..f52fda9 100644
--- a/app/aboot/mdtp_fs.c
+++ b/app/aboot/mdtp_fs.c
@@ -44,6 +44,63 @@
static mdtp_image_t mdtp_img;
/*---------------------------------------------------------
+ * Internal Functions
+ *-------------------------------------------------------*/
+
+static int mdtp_read_metadata(uint32_t offset){
+ int index = INVALID_PTN;
+ unsigned long long ptn = 0;
+ int i = 0;
+ uint32_t block_size = mmc_get_device_blocksize();
+
+ index = partition_get_index("mdtp");
+ if (index == 0) {
+ dprintf(CRITICAL, "ERROR: mdtp Partition table not found\n");
+ return -1;
+ }
+
+ ptn = partition_get_offset(index);
+ mmc_set_lun(partition_get_lun(index));
+
+ if (ptn == 0) {
+ dprintf(CRITICAL, "ERROR: mdtp Partition invalid\n");
+ return -1;
+ }
+
+ for(i = 0; i< MAX_PARAMS; i++) {
+ mdtp_img.meta_data.params[i] = MDTP_PARAM_UNSET_VALUE; //Initialize params for error check
+ }
+
+ uint8_t *base = memalign(block_size, ROUNDUP(MDTP_HEADER_LEN, block_size));
+ if (!base) {
+ dprintf(CRITICAL, "ERROR: mdtp malloc failed\n");
+ return -1;
+ }
+
+ // read image meta data
+ if (mmc_read(ptn+offset, (void*)base, MDTP_HEADER_LEN)) {
+ dprintf(CRITICAL, "ERROR: mdtp meta data read failed\n");
+ free(base);
+ return -1;
+ }
+
+ uint32_t params_size = MAX_PARAMS * sizeof(uint32_t);
+ uint32_t images_params_size = MAX_IMAGES*sizeof(mdtp_image_params_t);
+ memscpy(mdtp_img.meta_data.params, sizeof(mdtp_img.meta_data.params), base, params_size);
+ memscpy(mdtp_img.meta_data.image_params, META_DATA_PARTITION_LEN,
+ base + sizeof(mdtp_img.meta_data.params), images_params_size);
+
+ dprintf(INFO, "mdtp: metadata loaded\n");
+
+ free(base);
+ return 0;
+}
+
+static void mdtp_fs_set_param(mdtp_parameter_id_t param, uint32_t value){
+ mdtp_img.meta_data.params[param] = value;
+}
+
+/*---------------------------------------------------------
* External Functions
*-------------------------------------------------------*/
@@ -63,53 +120,90 @@
return mdtp_img.meta_data.params[param];
}
-
int mdtp_fs_init(){
- int index = INVALID_PTN;
- unsigned long long ptn = 0;
- int i = 0;
- uint32_t block_size = mmc_get_device_blocksize();
+ uint32_t i;
+ struct fbcon_config *fb_config = NULL;
+ mdtp_image_params_t image_params;
+ mdtp_image_t mdtp_image_sets_metadata;
+ uint32_t image_sets_num;
+ uint32_t metadata_offset = 0;
- index = partition_get_index("mdtp");
- if (index == 0) {
- dprintf(CRITICAL, "ERROR: mdtp Partition table not found\n");
- return 1;
+ // Read image sets metadata
+ if (mdtp_read_metadata(metadata_offset)){
+ dprintf(CRITICAL, "ERROR: failed to read image sets metadata\n");
+ return -1;
}
- ptn = partition_get_offset(index);
- mmc_set_lun(partition_get_lun(index));
-
- if (ptn == 0) {
- dprintf(CRITICAL, "ERROR: mdtp Partition invalid\n");
- return 1;
+ // Verify that metadata version is supported
+ if (mdtp_fs_get_param(VERSION) != SUPPORTED_METADATA_VERSION){
+ dprintf(CRITICAL, "ERROR: metadata version is not supported: %d\n", mdtp_fs_get_param(VERSION));
+ return -1;
}
- for(i = 0; i< MAX_PARAMS; i++) {
- mdtp_img.meta_data.params[i] = -1; //Initiate params for errors check
+ // Verify that metadata version is as expected
+ if (mdtp_fs_get_param(TYPE) != IMAGE_SETS){
+ dprintf(CRITICAL, "ERROR: unexpected type for image sets metadata: %d\n", mdtp_fs_get_param(TYPE));
+ return -1;
}
- uint8_t *base = memalign(block_size, ROUNDUP(MDTP_HEADER_LEN, block_size));
- if (!base) {
- dprintf(CRITICAL, "ERROR: mdtp malloc failed\n");
- return 1;
+ image_sets_num = mdtp_fs_get_param(IMAGE_SETS_NUM);
+ if (image_sets_num < 1) {
+ dprintf(CRITICAL, "ERROR: invalid number of image sets: %d\n", image_sets_num);
+ return -1;
}
- // read image meta data
- if (mmc_read(ptn, (void*)base, MDTP_HEADER_LEN)) {
- dprintf(CRITICAL, "ERROR: mdtp meta data read failed\n");
- free(base);
- return 1;
+ // Get screen configuration
+ fb_config = fbcon_display();
+
+ // Image sets are sorted by screen resolution (width, height), from low to high.
+ // We begin with the smallest image set, and check if bigger image sets also fit the screen.
+ image_params = mdtp_img.meta_data.image_params[0];
+
+ for (i=1; i<image_sets_num; i++){
+
+ //if both width and height still fit the screen, update image_params
+ if (mdtp_img.meta_data.image_params[i].width <= fb_config->width &&
+ mdtp_img.meta_data.image_params[i].height <= fb_config->height)
+ {
+ image_params = mdtp_img.meta_data.image_params[i];
+ }
+
+ // if we reached an image set in which the width is larger than
+ // the screen width, no point in checking additional image sets.
+ else if (mdtp_img.meta_data.image_params[i].width > fb_config->width)
+ break;
}
- uint32_t params_size = MAX_PARAMS * sizeof(uint32_t);
- uint32_t images_params_size = MAX_IMAGES*sizeof(mdtp_image_params_t);
- memscpy(mdtp_img.meta_data.params, sizeof(mdtp_img.meta_data.params), base, params_size);
- memscpy(mdtp_img.meta_data.image_params, META_DATA_PARTITION_LEN,
- base + sizeof(mdtp_img.meta_data.params), images_params_size);
+ dprintf(INFO, "mdtp: image set offset: 0x%x\n", image_params.offset);
+ dprintf(INFO, "mdtp: image set width: %d, screen width: %d\n", image_params.width, fb_config->width);
+ dprintf(INFO, "mdtp: image set height: %d, screen height: %d\n", image_params.height, fb_config->height);
+
+ // Backup image sets metadata for required parameters
+ mdtp_image_sets_metadata = mdtp_img;
+
+ // Read images metadata
+ if (mdtp_read_metadata(image_params.offset)){
+ dprintf(CRITICAL, "ERROR: failed to read images metadata\n");
+ return -1;
+ }
+
+ // Verify that metadata version is supported
+ if (mdtp_fs_get_param(VERSION) != SUPPORTED_METADATA_VERSION){
+ dprintf(CRITICAL, "ERROR: metadata version is not supported: %d\n", mdtp_fs_get_param(VERSION));
+ return -1;
+ }
+
+ // Verify that metadata version is as expected
+ if (mdtp_fs_get_param(TYPE) != IMAGES){
+ dprintf(CRITICAL, "ERROR: unexpected type for images metadata: %d\n", mdtp_fs_get_param(TYPE));
+ return -1;
+ }
+
+ // Copy eFuse from image sets metadata
+ mdtp_fs_set_param(VIRTUAL_FUSE, mdtp_image_sets_metadata.meta_data.params[VIRTUAL_FUSE]);
dprintf(INFO, "mdtp: mdtp_img loaded\n");
- free(base);
return 0;
}
diff --git a/app/aboot/mdtp_fs.h b/app/aboot/mdtp_fs.h
index 33ddf55..e131c12 100644
--- a/app/aboot/mdtp_fs.h
+++ b/app/aboot/mdtp_fs.h
@@ -29,19 +29,26 @@
#ifndef MDTP_FS_H
#define MDTP_FS_H
-#define MAX_IMAGES (40)
-#define MDTP_HEADER_LEN (4096)
-#define META_DATA_PARTITION_LEN (2048)
-#define MAX_PARAMS (512)
+#define MAX_IMAGES (40)
+#define MDTP_HEADER_LEN (4096)
+#define META_DATA_PARTITION_LEN (2048)
+#define MAX_PARAMS (512)
+#define MDTP_PARAM_UNSET_VALUE (111)
+#define SUPPORTED_METADATA_VERSION (1)
+
/*
-MDTP header layout:
+MDTP image layout:
+-The mdtp image file contains two layers that both include mdtp_img headers:
+ 1. The first header includes the image sets metadata.
+ 2. Once we decided which image set we would like to display, we read the metadata
+ of that specific image set (contains metadata of the actual images).
-The mdtp_img header is a fixed length of 4096 Bytes.
--The mdtp_img header is devided into 2 partitions:
+-The mdtp_img header is divided into 2 partitions:
1.MDTP parameters (eFuse, digit-space, etc..)
- 2.Images meta-data (offset, width, height)
+ 2.Images/image sets meta-data (offset, width, height)
-Each partition size is 2048 Bytes.
--Each parameter is 4 Bytes long, 512 params MAX.
--Each meta-data part (offset/width/height) is 4 Bytes long.
+-Each parameter is 4 Bytes long, 512 params max.
+-Each meta-data parameter (offset/width/height) is 4 Bytes long.
*/
@@ -76,7 +83,9 @@
PIN_UNSELECTED_6 = 24, PIN_UNSELECTED_7 = 25,
PIN_UNSELECTED_8 = 26, PIN_UNSELECTED_9 = 27} mdtp_image_id_t;
-typedef enum {VIRTUAL_FUSE = 0, DIGIT_SPACE = 1} mdtp_parameter_id_t ;
+typedef enum {VIRTUAL_FUSE = 0, DIGIT_SPACE = 1, VERSION = 2, TYPE = 3, IMAGE_SETS_NUM = 4} mdtp_parameter_id_t;
+
+typedef enum {IMAGES = 1, IMAGE_SETS = 2} mdtp_metadata_type_t;
/*---------------------------------------------------------
* External Functions
diff --git a/app/aboot/mdtp_fuse.c b/app/aboot/mdtp_fuse.c
index 439fb73..44d2eb5 100644
--- a/app/aboot/mdtp_fuse.c
+++ b/app/aboot/mdtp_fuse.c
@@ -43,7 +43,7 @@
typedef union
{
- struct {
+ struct {
uint8_t enable1 : 1;
uint8_t disable1 : 1;
uint8_t enable2 : 1;
@@ -79,7 +79,7 @@
#define SHK_FUSE 0x02
#define DEBUG_FUSE 0x04
- /* Make sure we only read the test mode once */
+ /* Make sure we only read the test mode once */
if (test_mode_set)
return test_mode;
@@ -95,7 +95,7 @@
{
dprintf(CRITICAL, "mdtp: is_test_mode: qsee_get_secure_state returned error: %d, status.value[0]: %d\n", ret, status_low);
test_mode = 0;
- }
+ }
test_mode_set = 1;
dprintf(INFO, "mdtp: is_test_mode: test mode is set to %d\n", test_mode);
@@ -111,7 +111,7 @@
static int read_metadata(metadata_t *metadata)
{
int eFuse = mdtp_fs_get_param(VIRTUAL_FUSE);
- if(eFuse == -1){ //Error initiating eFuse
+ if(eFuse == MDTP_PARAM_UNSET_VALUE){ //Error initializing eFuse
dprintf(CRITICAL, "mdtp: eFuse reading error\n");
return -1;
}
@@ -215,8 +215,8 @@
}
if (!(eFuses.bitwise.enable1 && !eFuses.bitwise.disable1) &&
- !(eFuses.bitwise.enable2 && !eFuses.bitwise.disable2) &&
- !(eFuses.bitwise.enable3 && !eFuses.bitwise.disable3))
+ !(eFuses.bitwise.enable2 && !eFuses.bitwise.disable2) &&
+ !(eFuses.bitwise.enable3 && !eFuses.bitwise.disable3))
{
*enabled = 0;
}
diff --git a/app/aboot/mdtp_ui.c b/app/aboot/mdtp_ui.c
index fafb787..ed14e65 100644
--- a/app/aboot/mdtp_ui.c
+++ b/app/aboot/mdtp_ui.c
@@ -33,10 +33,11 @@
#include <partition_parser.h>
#include <stdlib.h>
#include <string.h>
+#include <display_menu.h>
+#include <qtimer.h>
#include "mdtp.h"
#include "mdtp_defs.h"
#include "mdtp_fs.h"
-#include <display_menu.h>
// Image releative locations
#define ERROR_MESSAGE_RELATIVE_Y_LOCATION (0.18)
@@ -54,15 +55,14 @@
#define CENTER_IMAGE_ON_X_AXIS(image_width,screen_width) (((screen_width)-(image_width))/2)
-extern void mdelay(unsigned msecs);
extern uint32_t target_volume_up();
extern uint32_t target_volume_down();
extern int msm_display_on();
struct mdtp_fbimage {
- uint32_t width;
- uint32_t height;
- uint8_t image[MDTP_MAX_IMAGE_SIZE];
+ uint32_t width;
+ uint32_t height;
+ uint8_t image[MDTP_MAX_IMAGE_SIZE];
};
/*----------------------------------------------------------------------------
@@ -71,6 +71,7 @@
static uint32_t g_pin_frames_x_location[MDTP_PIN_LEN] = {0};
static uint32_t g_pin_frames_y_location = 0;
+static bool g_diplay_pin = false;
static bool g_initial_screen_displayed = false;
@@ -130,9 +131,9 @@
unsigned bytes_per_bpp = ((fb_config->bpp) / BITS_PER_BYTE);
if (mmc_read(ptn+offset, (void*)base, ROUNDUP(width*height*bytes_per_bpp, block_size))) {
- fbcon_clear();
- dprintf(CRITICAL, "ERROR: mdtp image read failed\n");
- return NULL;
+ fbcon_clear();
+ dprintf(CRITICAL, "ERROR: mdtp image read failed\n");
+ return NULL;
}
logo->width = width;
@@ -167,7 +168,7 @@
if (fb_config)
{
- image_base = (y *(fb_config->width));
+ image_base = (y *(fb_config->width));
bytes_per_bpp = ((fb_config->bpp) / BITS_PER_BYTE);
unsigned count = fb_config->width*section_height;
@@ -177,8 +178,8 @@
}
else
{
- dprintf(CRITICAL,"ERROR: fbcon_config struct is NULL\n");
- display_error_msg(); /* This will never return */
+ dprintf(CRITICAL,"ERROR: fbcon_config struct is NULL\n");
+ display_error_msg(); /* This will never return */
}
}
@@ -189,13 +190,13 @@
*/
static void fbcon_putImage_in_location(struct mdtp_fbimage *fbimg, uint32_t x, uint32_t y)
{
- unsigned i = 0;
- unsigned bytes_per_bpp;
- unsigned image_base;
- unsigned width, pitch, height;
- unsigned char *logo_base = NULL;
+ unsigned i = 0;
+ unsigned bytes_per_bpp;
+ unsigned image_base;
+ unsigned width, pitch, height;
+ unsigned char *logo_base = NULL;
- if (!fb_config) {
+ if (!fb_config) {
dprintf(CRITICAL,"ERROR: NULL configuration, image cannot be displayed\n");
return;
}
@@ -206,8 +207,8 @@
logo_base = (unsigned char *)fbimg->image;
}
else {
- dprintf(CRITICAL,"ERROR: invalid image struct\n");
- return;
+ dprintf(CRITICAL,"ERROR: invalid image struct\n");
+ return;
}
bytes_per_bpp = ((fb_config->bpp) / BITS_PER_BYTE);
@@ -222,16 +223,16 @@
}
if (fbimg->width > fb_config->width || fbimg->height > fb_config->height ||
- (x > (fb_config->width - fbimg->width)) || (y > (fb_config->height - fbimg->height)))
+ (x > (fb_config->width - fbimg->width)) || (y > (fb_config->height - fbimg->height)))
{
- dprintf(CRITICAL,"ERROR: invalid image size, larger than the screen or exceeds its margins\n");
- return;
+ dprintf(CRITICAL,"ERROR: invalid image size, larger than the screen or exceeds its margins\n");
+ return;
}
image_base = ( (y *(fb_config->width)) + x);
for (i = 0; i < height; i++) {
memcpy (fb_config->base + ((image_base + (i * (fb_config->width))) * bytes_per_bpp),
- logo_base + ((height - 1 - i) * pitch * bytes_per_bpp), width * bytes_per_bpp);
+ logo_base + ((height - 1 - i) * pitch * bytes_per_bpp), width * bytes_per_bpp);
}
}
else
@@ -254,26 +255,26 @@
*/
static int display_error_message()
{
- struct mdtp_fbimage *fbimg;
+ struct mdtp_fbimage *fbimg;
- if (fb_config)
+ if (fb_config)
{
- uint32_t x = CENTER_IMAGE_ON_X_AXIS(get_image_width(ALERT_MESSAGE),fb_config->width);
+ uint32_t x = CENTER_IMAGE_ON_X_AXIS(get_image_width(ALERT_MESSAGE),fb_config->width);
uint32_t y = ((fb_config->height)*ERROR_MESSAGE_RELATIVE_Y_LOCATION);
- fbimg = mdtp_read_mmc_image(get_image_offset(ALERT_MESSAGE),get_image_width(ALERT_MESSAGE), get_image_height(ALERT_MESSAGE));
- if (NULL == fbimg)
- {
- dprintf(CRITICAL,"ERROR: failed to read error image from mmc\n");
- return -1;
- }
+ fbimg = mdtp_read_mmc_image(get_image_offset(ALERT_MESSAGE),get_image_width(ALERT_MESSAGE), get_image_height(ALERT_MESSAGE));
+ if (NULL == fbimg)
+ {
+ dprintf(CRITICAL,"ERROR: failed to read error image from mmc\n");
+ return -1;
+ }
- fbcon_putImage_in_location(fbimg, x, y);
+ fbcon_putImage_in_location(fbimg, x, y);
return 0;
}
else
{
- dprintf(CRITICAL,"ERROR: fbcon_config struct is NULL\n");
+ dprintf(CRITICAL,"ERROR: fbcon_config struct is NULL\n");
return -1;
}
}
@@ -284,24 +285,24 @@
*/
static void display_image(uint32_t offset, uint32_t width, uint32_t height, uint32_t x, uint32_t y)
{
- struct mdtp_fbimage *fbimg;
+ struct mdtp_fbimage *fbimg;
- if (fb_config)
- {
- fbimg = mdtp_read_mmc_image(offset, width, height);
- if (NULL == fbimg)
- {
- dprintf(CRITICAL,"ERROR: failed to read image from mmc\n");
- display_error_msg(); /* This will never return */
- }
+ if (fb_config)
+ {
+ fbimg = mdtp_read_mmc_image(offset, width, height);
+ if (NULL == fbimg)
+ {
+ dprintf(CRITICAL,"ERROR: failed to read image from mmc\n");
+ display_error_msg(); /* This will never return */
+ }
- fbcon_putImage_in_location(fbimg, x, y);
- }
- else
- {
- dprintf(CRITICAL,"ERROR: fbcon_config struct is NULL\n");
- display_error_msg(); /* This will never return */
- }
+ fbcon_putImage_in_location(fbimg, x, y);
+ }
+ else
+ {
+ dprintf(CRITICAL,"ERROR: fbcon_config struct is NULL\n");
+ display_error_msg(); /* This will never return */
+ }
}
/**
@@ -329,7 +330,7 @@
*/
static void display_invalid_pin()
{
- uint32_t x = CENTER_IMAGE_ON_X_AXIS(get_image_width(MAINTEXT_INCORRECTPIN),fb_config->width);
+ uint32_t x = CENTER_IMAGE_ON_X_AXIS(get_image_width(MAINTEXT_INCORRECTPIN),fb_config->width);
uint32_t y = (fb_config->height)*MAIN_TEXT_RELATIVE_Y_LOCATION;
display_image(get_image_offset(MAINTEXT_INCORRECTPIN), get_image_width(MAINTEXT_INCORRECTPIN), get_image_height(MAINTEXT_INCORRECTPIN), x, y);
@@ -340,7 +341,7 @@
*/
static void display_digits_instructions()
{
- uint32_t x = CENTER_IMAGE_ON_X_AXIS(get_image_width(PINTEXT),fb_config->width);
+ uint32_t x = CENTER_IMAGE_ON_X_AXIS(get_image_width(PINTEXT),fb_config->width);
uint32_t y = (fb_config->height)*PIN_TEXT_RELATIVE_Y_LOCATION;
display_image(get_image_offset(PINTEXT), get_image_width(PINTEXT), get_image_height(PINTEXT), x, y);
@@ -351,8 +352,8 @@
*/
static void clear_digits_instructions()
{
- uint32_t y = (fb_config->height)*PIN_TEXT_RELATIVE_Y_LOCATION;
- fbcon_clear_section(y, get_image_height(PINTEXT));
+ uint32_t y = (fb_config->height)*PIN_TEXT_RELATIVE_Y_LOCATION;
+ fbcon_clear_section(y, get_image_height(PINTEXT));
}
/**
@@ -360,8 +361,11 @@
*/
static void display_digit(uint32_t x, uint32_t y, uint32_t digit)
{
- display_image(get_image_offset(PIN_UNSELECTED_0 + digit),
- get_image_width(PIN_UNSELECTED_0 + digit), get_image_height(PIN_UNSELECTED_0 + digit), x, y);
+ if (g_diplay_pin == false)
+ return;
+
+ display_image(get_image_offset(PIN_UNSELECTED_0 + digit),
+ get_image_width(PIN_UNSELECTED_0 + digit), get_image_height(PIN_UNSELECTED_0 + digit), x, y);
}
/**
@@ -369,6 +373,9 @@
*/
static void display_selected_digit(uint32_t x, uint32_t y, uint32_t digit)
{
+ if (g_diplay_pin == false)
+ return;
+
display_image(get_image_offset(PIN_SELECTED_0 + digit),
get_image_width(PIN_SELECTED_0 + digit),
get_image_height(PIN_SELECTED_0 + digit), x, y);
@@ -379,7 +386,7 @@
*/
static void display_ok_button()
{
- uint32_t ok_x = CENTER_IMAGE_ON_X_AXIS(get_image_width(BTN_OK_OFF),fb_config->width);
+ uint32_t ok_x = CENTER_IMAGE_ON_X_AXIS(get_image_width(BTN_OK_OFF),fb_config->width);
uint32_t ok_y = (fb_config->height)*OK_BUTTON_RELATIVE_Y_LOCATION;
display_image(get_image_offset(BTN_OK_OFF), get_image_width(BTN_OK_OFF),get_image_height(BTN_OK_OFF), ok_x, ok_y);
@@ -390,7 +397,7 @@
*/
static void display_selected_ok_button()
{
- uint32_t ok_x = CENTER_IMAGE_ON_X_AXIS(get_image_width(BTN_OK_ON),fb_config->width);
+ uint32_t ok_x = CENTER_IMAGE_ON_X_AXIS(get_image_width(BTN_OK_ON),fb_config->width);
uint32_t ok_y = (fb_config->height)*OK_BUTTON_RELATIVE_Y_LOCATION;
display_image(get_image_offset(BTN_OK_ON), get_image_width(BTN_OK_ON), get_image_height(BTN_OK_ON), ok_x, ok_y);
@@ -402,7 +409,7 @@
*/
static void display_pin_instructions()
{
- uint32_t x = CENTER_IMAGE_ON_X_AXIS(get_image_width(ACCEPTEDIT_TEXT),fb_config->width);
+ uint32_t x = CENTER_IMAGE_ON_X_AXIS(get_image_width(ACCEPTEDIT_TEXT),fb_config->width);
uint32_t y = (fb_config->height)*OK_TEXT_RELATIVE_Y_LOCATION;
display_image(get_image_offset(ACCEPTEDIT_TEXT), get_image_width(ACCEPTEDIT_TEXT), get_image_height(ACCEPTEDIT_TEXT), x, y);
@@ -413,7 +420,7 @@
*/
static void clear_pin_message()
{
- uint32_t y = (fb_config->height)*OK_TEXT_RELATIVE_Y_LOCATION;
+ uint32_t y = (fb_config->height)*OK_TEXT_RELATIVE_Y_LOCATION;
fbcon_clear_section(y,get_image_height(ACCEPTEDIT_TEXT));
}
@@ -442,7 +449,7 @@
fbcon_clear();
if (display_error_message())
- display_error_msg(); /* This will never return */
+ display_error_msg(); /* This will never return */
display_initial_delay();
mdelay(INITIAL_DELAY_MSECONDS);
@@ -450,16 +457,26 @@
g_pin_frames_y_location = ((fb_config->height)*PIN_RELATIVE_Y_LOCATION);
uint32_t total_pin_length = pin_length*get_image_width(PIN_UNSELECTED_0) + mdtp_fs_get_param(DIGIT_SPACE)*(pin_length - 1);
- uint32_t complete_pin_centered = (fb_config->width - total_pin_length)/2;
- for (uint32_t i=0; i<pin_length; i++)
+ if (fb_config->width > total_pin_length)
{
- g_pin_frames_x_location[i] = complete_pin_centered + i*(mdtp_fs_get_param(DIGIT_SPACE) + get_image_width(PIN_UNSELECTED_0));
+ g_diplay_pin = true;
+
+ uint32_t complete_pin_centered = (fb_config->width - total_pin_length)/2;
+
+ for (uint32_t i=0; i<pin_length; i++)
+ {
+ g_pin_frames_x_location[i] = complete_pin_centered + i*(mdtp_fs_get_param(DIGIT_SPACE) + get_image_width(PIN_UNSELECTED_0));
+ }
+
+ for (uint32_t i=0; i<pin_length; i++)
+ {
+ display_digit(g_pin_frames_x_location[i], g_pin_frames_y_location, 0);
+ }
}
-
- for (uint32_t i=0; i<pin_length; i++)
+ else
{
- display_digit(g_pin_frames_x_location[i], g_pin_frames_y_location, 0);
+ dprintf(CRITICAL,"ERROR: screen is not wide enough, PIN digits can't be displayed\n");
}
display_ok_button();
@@ -468,8 +485,8 @@
}
else
{
- dprintf(CRITICAL,"ERROR: fbcon_config struct is NULL\n");
- display_error_msg(); /* This will never return */
+ dprintf(CRITICAL,"ERROR: fbcon_config struct is NULL\n");
+ display_error_msg(); /* This will never return */
}
}
@@ -574,12 +591,12 @@
*/
void display_invalid_pin_msg()
{
- clear_pin_message();
- display_ok_button();
+ clear_pin_message();
+ display_ok_button();
- display_invalid_pin();
+ display_invalid_pin();
- mdelay(INVALID_PIN_DELAY_MSECONDS);
+ mdelay(INVALID_PIN_DELAY_MSECONDS);
}
/**
diff --git a/include/dev/flash.h b/include/dev/flash.h
index 9c41561..f908db8 100644
--- a/include/dev/flash.h
+++ b/include/dev/flash.h
@@ -77,6 +77,8 @@
{
return flash_read_ext(ptn, 0, offset, data, bytes);
}
+
+unsigned flash_num_pages_per_blk(void);
unsigned flash_page_size(void);
unsigned flash_block_size(void);
unsigned flash_spare_size(void);
diff --git a/include/target.h b/include/target.h
index e0a0264..d0d830d 100644
--- a/include/target.h
+++ b/include/target.h
@@ -70,6 +70,7 @@
const char * target_usb_controller();
void target_usb_phy_reset(void);
+void target_usb_phy_sec_reset(void);
void target_usb_phy_mux_configure(void);
target_usb_iface_t * target_usb30_init();
bool target_is_cdp_qvga();
diff --git a/lib/heap/heap.c b/lib/heap/heap.c
index a4835f9..2f41f6c 100644
--- a/lib/heap/heap.c
+++ b/lib/heap/heap.c
@@ -156,19 +156,19 @@
// nearby ones if possible. Returns base of whatever chunk it became in the list.
static struct free_heap_chunk *heap_insert_free_chunk(struct free_heap_chunk *chunk)
{
-#if DEBUGLEVEL > INFO
+#if DEBUG_HEAP
vaddr_t chunk_end = (vaddr_t)chunk + chunk->len;
+ dprintf(CRITICAL,"%s: chunk ptr %p, size 0x%lx, chunk_end 0x%x\n",
+ __FUNCTION__, chunk, chunk->len, chunk_end);
#endif
-// dprintf("%s: chunk ptr %p, size 0x%lx, chunk_end 0x%x\n", __FUNCTION__, chunk, chunk->len, chunk_end);
-
struct free_heap_chunk *next_chunk;
struct free_heap_chunk *last_chunk;
// walk through the list, finding the node to insert before
list_for_every_entry(&theheap.free_list, next_chunk, struct free_heap_chunk, node) {
if (chunk < next_chunk) {
- DEBUG_ASSERT(chunk_end <= (vaddr_t)next_chunk);
+ DEBUG_ASSERT(((vaddr_t)chunk + chunk->len) <= (vaddr_t)next_chunk);
list_add_before(&next_chunk->node, &chunk->node);
diff --git a/platform/msm8996/acpuclock.c b/platform/msm8996/acpuclock.c
index 7ed7ff6..ff0b55c 100644
--- a/platform/msm8996/acpuclock.c
+++ b/platform/msm8996/acpuclock.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2014-2015, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2014-2016, The Linux Foundation. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
@@ -208,6 +208,40 @@
writel(reg, GCC_USB30_GDSCR);
}
+/* enables usb20 clocks */
+void clock_usb20_init(void)
+{
+ int ret;
+
+ ret = clk_get_set_enable("usb20_noc_usb20_clk", 0, true);
+ if(ret)
+ {
+ dprintf(CRITICAL, "failed to set usb20_noc_clk. ret = %d\n", ret);
+ ASSERT(0);
+ }
+
+ ret = clk_get_set_enable("usb20_master_clk", 120000000, true);
+ if(ret)
+ {
+ dprintf(CRITICAL, "failed to set usb20_master_clk. ret = %d\n", ret);
+ ASSERT(0);
+ }
+
+ ret = clk_get_set_enable("usb20_mock_utmi_clk", 60000000, true);
+ if(ret)
+ {
+ dprintf(CRITICAL, "failed to set usb20_mock_utmi_clk ret = %d\n", ret);
+ ASSERT(0);
+ }
+
+ ret = clk_get_set_enable("usb20_sleep_clk", 0, true);
+ if(ret)
+ {
+ dprintf(CRITICAL, "failed to set usb2_sleep_clk ret = %d\n", ret);
+ ASSERT(0);
+ }
+}
+
/* enables usb30 clocks */
void clock_usb30_init(void)
{
@@ -653,4 +687,37 @@
dprintf(CRITICAL, "Failed to enable %s\n", clk_name);
return;
}
-}
\ No newline at end of file
+}
+
+void hdmi_clk_enable(void)
+{
+ int ret;
+
+ /* Configure hdmi ahb clock */
+ ret = clk_get_set_enable("hdmi_ahb_clk", 0, 1);
+ if(ret) {
+ dprintf(CRITICAL, "failed to set hdmi_ahb_clk ret = %d\n", ret);
+ ASSERT(0);
+ }
+
+ /* Configure hdmi core clock */
+ ret = clk_get_set_enable("hdmi_core_clk", 19200000, 1);
+ if(ret) {
+ dprintf(CRITICAL, "failed to set hdmi_core_clk ret = %d\n", ret);
+ ASSERT(0);
+ }
+
+ /* Configure hdmi pixel clock */
+ ret = clk_get_set_enable("hdmi_extp_clk", 148500000, 1);
+ if(ret) {
+ dprintf(CRITICAL, "failed to set hdmi_extp_clk ret = %d\n", ret);
+ ASSERT(0);
+ }
+}
+
+void hdmi_clk_disable(void)
+{
+ clk_disable(clk_get("hdmi_extp_clk"));
+ clk_disable(clk_get("hdmi_core_clk"));
+ clk_disable(clk_get("hdmi_ahb_clk"));
+}
diff --git a/platform/msm8996/include/platform/clock.h b/platform/msm8996/include/platform/clock.h
index 01a551e..25e6ea9 100644
--- a/platform/msm8996/include/platform/clock.h
+++ b/platform/msm8996/include/platform/clock.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2014-2015, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2014-2016, The Linux Foundation. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
@@ -58,6 +58,13 @@
#define MMSS_MMAGIC_AHB_CBCR REG_MM(0x5024)
#define SMMU_MDP_AHB_CBCR REG_MM(0x2454)
#define MDSS_AHB_CBCR REG_MM(0x2308)
+#define MDSS_HDMI_AHB_CBCR REG_MM(0x230C)
+#define MDSS_HDMI_CBCR REG_MM(0x2338)
+#define MDSS_EXTPCLK_CBCR REG_MM(0x2324)
+#define EXTPCLK_CMD_RCGR REG_MM(0x2060)
+#define EXTPCLK_CFG_RCGR REG_MM(0x2064)
+#define HDMI_CMD_RCGR REG_MM(0x2100)
+#define HDMI_CFG_RCGR REG_MM(0x2104)
#define AXI_CMD_RCGR REG_MM(0x5040)
#define AXI_CFG_RCGR REG_MM(0x5044)
@@ -111,6 +118,7 @@
void clock_ce_enable(uint8_t instance);
void clock_ce_disable(uint8_t instance);
void clock_usb30_init(void);
+void clock_usb20_init(void);
void clock_reset_usb_phy();
void mmss_dsi_clock_enable(uint32_t cfg_rcgr, uint32_t dual_dsi);
@@ -125,4 +133,7 @@
void video_gdsc_disable();
void clock_config_blsp_i2c(uint8_t blsp_id, uint8_t qup_id);
+void hdmi_clk_enable(void);
+void hdmi_clk_disable(void);
+
#endif
diff --git a/platform/msm8996/include/platform/iomap.h b/platform/msm8996/include/platform/iomap.h
index 2fb9c8a..8ca4d18 100644
--- a/platform/msm8996/include/platform/iomap.h
+++ b/platform/msm8996/include/platform/iomap.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2014-2015, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2014-2016, The Linux Foundation. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
@@ -75,15 +75,33 @@
#define GCC_BLSP2_QUP2_CFG_RCGR (CLK_CTL_BASE + 0x28010)
#define GCC_BLSP2_QUP2_CMD_RCGR (CLK_CTL_BASE + 0x2800C)
+/* USB platform specific bases*/
+unsigned int usb_ctrl_base();
+unsigned int usb_qscratch_base();
+unsigned int usb_phy_base();
+unsigned int usb_phy_bcr();
+
+#define MSM_USB30_BASE (usb_ctrl_base())
+#define MSM_USB30_QSCRATCH_BASE (usb_qscratch_base())
+#define QUSB2_PHY_BASE (usb_phy_base())
+#define GCC_QUSB2_PHY_BCR (usb_phy_bcr())
+
/* USB3.0 */
-#define MSM_USB30_BASE 0x6A00000
-#define MSM_USB30_QSCRATCH_BASE 0x6AF8800
+#define MSM_USB30_PRIM_BASE 0x6A00000
+#define MSM_USB30_QSCRATCH_PRIM_BASE 0x6AF8800
+/* USB2.0 */
+#define MSM_USB20_SEC_BASE 0x7600000
+#define MSM_USB20_SEC_QSCRATCH_BASE 0x76F8800
/* SS QMP (Qulacomm Multi Protocol) */
#define QMP_PHY_BASE 0x7410000
-/* QUSB2 PHY */
-#define QUSB2_PHY_BASE 0x7411000
-#define GCC_QUSB2_PHY_BCR (CLK_CTL_BASE + 0x00012038)
+/* QUSB2 PHY primary */
+#define QUSB2_PRIM_PHY_BASE 0x7411000
+#define GCC_QUSB2_PRIM_PHY_BCR (CLK_CTL_BASE + 0x00012038)
+
+/* QUSB2 PHY secondary */
+#define QUSB2_SEC_PHY_BASE 0x7412000
+#define GCC_QUSB2_SEC_PHY_BCR (CLK_CTL_BASE + 0x0001203C)
#define AHB2_PHY_BASE 0x7416000
#define PERIPH_SS_AHB2PHY_TOP_CFG (AHB2_PHY_BASE + 0x10)
@@ -138,6 +156,20 @@
#define USB_PHY_CFG_AHB2PHY_CBCR (CLK_CTL_BASE + 0x6A004)
#define GCC_AGGRE2_USB3_AXI_CBCR (CLK_CTL_BASE + 0x83018)
+/* USB20 clocks */
+#define USB_20_BCR (CLK_CTL_BASE + 0x12000)
+#define USB20_MASTER_CBCR (CLK_CTL_BASE + 0x12004)
+#define USB20_SLEEP_CBCR (CLK_CTL_BASE + 0x12008)
+#define USB20_MOCK_UTMI_CBCR (CLK_CTL_BASE + 0x1200C)
+#define USB20_MASTER_CMD_RCGR (CLK_CTL_BASE + 0x12010)
+#define USB20_MASTER_CFG_RCGR (CLK_CTL_BASE + 0x12014)
+#define USB20_MASTER_M (CLK_CTL_BASE + 0x12018)
+#define USB20_MASTER_N (CLK_CTL_BASE + 0x1201c)
+#define USB20_MASTER_D (CLK_CTL_BASE + 0x12020)
+#define USB20_MOCK_UTMI_CMD_RCGR (CLK_CTL_BASE + 0x12024)
+#define USB20_MOCK_UTMI_CFG_RCGR (CLK_CTL_BASE + 0x12028)
+#define PERIPH_NOC_USB20_AHB_CBCR (CLK_CTL_BASE + 0x06010)
+
/* SDCC */
#define SDCC1_BCR (CLK_CTL_BASE + 0x13000) /* block reset */
#define SDCC1_APPS_CBCR (CLK_CTL_BASE + 0x13004) /* branch control */
@@ -209,7 +241,7 @@
* as device memory, define the start address
* and size in MB
*/
-#define RPMB_SND_RCV_BUF 0x91A00000
+#define RPMB_SND_RCV_BUF 0x91C00000
#define RPMB_SND_RCV_BUF_SZ 0x2
#define TCSR_BOOT_MISC_DETECT 0x007B3000
@@ -308,6 +340,11 @@
#endif
#define MDP_INTF_2_TIMING_ENGINE_EN REG_MDP(0x6C000)
+#ifdef MDP_INTF_3_TIMING_ENGINE_EN
+#undef MDP_INTF_3_TIMING_ENGINE_EN
+#endif
+#define MDP_INTF_3_TIMING_ENGINE_EN REG_MDP(0x6C800)
+
#ifdef MDP_CTL_0_BASE
#undef MDP_CTL_0_BASE
#endif
@@ -348,6 +385,11 @@
#endif
#define MDP_INTF_2_BASE REG_MDP(0x6c000)
+#ifdef MDP_INTF_3_BASE
+#undef MDP_INTF_3_BASE
+#endif
+#define MDP_INTF_3_BASE REG_MDP(0x6c800)
+
#ifdef MDP_CLK_CTRL0
#undef MDP_CLK_CTRL0
#endif
@@ -565,4 +607,59 @@
#define APPS_WDOG_RESET_REG (APSS_WDOG_BASE + 0x04)
#define APPS_WDOG_CTL_REG (APSS_WDOG_BASE + 0x08)
+/* HDMI reg addresses */
+#define HDMI_BASE 0x9A0000
+#define REG_HDMI(off) (HDMI_BASE + (off))
+
+#define HDMI_ACR_32_0 REG_HDMI(0xC4)
+#define HDMI_ACR_32_1 REG_HDMI(0xC8)
+#define HDMI_ACR_44_0 REG_HDMI(0xCC)
+#define HDMI_ACR_44_1 REG_HDMI(0xD0)
+#define HDMI_ACR_48_0 REG_HDMI(0xD4)
+#define HDMI_ACR_48_1 REG_HDMI(0xD8)
+#define HDMI_AUDIO_PKT_CTRL2 REG_HDMI(0x44)
+#define HDMI_ACR_PKT_CTRL REG_HDMI(0x24)
+#define HDMI_INFOFRAME_CTRL0 REG_HDMI(0x2C)
+#define HDMI_AUDIO_INFO0 REG_HDMI(0xE4)
+#define HDMI_AUDIO_INFO1 REG_HDMI(0xE8)
+#define HDMI_AUDIO_PKT_CTRL REG_HDMI(0x20)
+#define HDMI_VBI_PKT_CTRL REG_HDMI(0x28)
+#define HDMI_GEN_PKT_CTRL REG_HDMI(0x34)
+#define HDMI_GC REG_HDMI(0x40)
+#define HDMI_AUDIO_CFG REG_HDMI(0x1D0)
+
+#define HDMI_DDC_SPEED REG_HDMI(0x220)
+#define HDMI_DDC_SETUP REG_HDMI(0x224)
+#define HDMI_DDC_REF REG_HDMI(0x27C)
+#define HDMI_DDC_DATA REG_HDMI(0x238)
+#define HDMI_DDC_TRANS0 REG_HDMI(0x228)
+#define HDMI_DDC_TRANS1 REG_HDMI(0x22C)
+#define HDMI_DDC_CTRL REG_HDMI(0x20C)
+#define HDMI_DDC_INT_CTRL REG_HDMI(0x214)
+#define HDMI_DDC_SW_STATUS REG_HDMI(0x218)
+#define HDMI_DDC_ARBITRATION REG_HDMI(0x210)
+
+#define HDMI_USEC_REFTIMER REG_HDMI(0x208)
+#define HDMI_CTRL REG_HDMI(0x000)
+#define HDMI_HPD_INT_STATUS REG_HDMI(0x250)
+#define HDMI_HPD_INT_CTRL REG_HDMI(0x254)
+#define HDMI_HPD_CTRL REG_HDMI(0x258)
+#define HDMI_PHY_CTRL REG_HDMI(0x2D4)
+#define HDMI_TOTAL REG_HDMI(0x2C0)
+#define HDMI_ACTIVE_H REG_HDMI(0x2B4)
+#define HDMI_ACTIVE_V REG_HDMI(0x2B8)
+#define HDMI_V_TOTAL_F2 REG_HDMI(0x2C4)
+#define HDMI_ACTIVE_V_F2 REG_HDMI(0x2BC)
+#define HDMI_FRAME_CTRL REG_HDMI(0x2C8)
+
+#define HDMI_AVI_INFO0 REG_HDMI(0x06C)
+#define HDMI_AVI_INFO1 REG_HDMI(0x070)
+#define HDMI_AVI_INFO2 REG_HDMI(0x074)
+#define HDMI_AVI_INFO3 REG_HDMI(0x078)
+
+#define LPASS_LPAIF_RDDMA_CTL0 0x0910D000
+#define LPASS_LPAIF_RDDMA_BASE0 0x0910D004
+#define LPASS_LPAIF_RDDMA_BUFF_LEN0 0x0910D008
+#define LPASS_LPAIF_RDDMA_PER_LEN0 0x0910D010
+#define LPASS_LPAIF_DEBUG_CTL 0x0910000C
#endif
diff --git a/platform/msm8996/include/platform/irqs.h b/platform/msm8996/include/platform/irqs.h
index 61d267b..e5cc23d 100644
--- a/platform/msm8996/include/platform/irqs.h
+++ b/platform/msm8996/include/platform/irqs.h
@@ -45,7 +45,13 @@
#define INT_QTMR_FRM_0_PHYSICAL_TIMER_EXP (GIC_SPI_START + 31)
-#define USB30_EE1_IRQ (GIC_SPI_START + 131)
+/* to support secondary port usage, secondary port Interrupt*/
+int usb_irq();
+
+#define USB30_EE1_IRQ (usb_irq())
+
+#define USB30_IRQ (GIC_SPI_START + 131)
+#define USB20_IRQ (GIC_SPI_START + 138)
#define GLINK_IPC_IRQ (GIC_SPI_START + 168)
diff --git a/platform/msm8996/msm8996-clock.c b/platform/msm8996/msm8996-clock.c
index 782a624..9074bd6 100644
--- a/platform/msm8996/msm8996-clock.c
+++ b/platform/msm8996/msm8996-clock.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2014-2015, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2014-2016, The Linux Foundation. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
@@ -46,6 +46,7 @@
#define mmpll1_mm_source_val 2
#define mmpll3_mm_source_val 3
#define gpll0_mm_source_val 5
+#define hdmipll_mm_source_val 3
struct clk_freq_tbl rcg_dummy_freq = F_END;
@@ -335,6 +336,16 @@
},
};
+static struct branch_clk gcc_periph_noc_usb20_ahb_clk = {
+ .cbcr_reg = (uint32_t *) PERIPH_NOC_USB20_AHB_CBCR,
+ .has_sibling = 1,
+
+ .c = {
+ .dbg_name = "periph_noc_usb20_ahb_clk",
+ .ops = &clk_ops_branch,
+ },
+};
+
static struct clk_freq_tbl ftbl_gcc_usb30_master_clk[] = {
F( 19200000, cxo, 1, 0, 0),
F( 120000000, gpll0, 5, 0, 0),
@@ -342,6 +353,13 @@
F_END
};
+static struct clk_freq_tbl ftbl_gcc_usb20_master_clk[] = {
+ F( 19200000, cxo, 1, 0, 0),
+ F( 120000000, gpll0, 5, 0, 0),
+ F( 150000000, gpll0, 4, 0, 0),
+ F_END
+};
+
static struct rcg_clk usb30_master_clk_src = {
.cmd_reg = (uint32_t *) USB30_MASTER_CMD_RCGR,
.cfg_reg = (uint32_t *) USB30_MASTER_CFG_RCGR,
@@ -359,6 +377,23 @@
},
};
+static struct rcg_clk usb20_master_clk_src = {
+ .cmd_reg = (uint32_t *) USB20_MASTER_CMD_RCGR,
+ .cfg_reg = (uint32_t *) USB20_MASTER_CFG_RCGR,
+ .m_reg = (uint32_t *) USB20_MASTER_M,
+ .n_reg = (uint32_t *) USB20_MASTER_N,
+ .d_reg = (uint32_t *) USB20_MASTER_D,
+
+ .set_rate = clock_lib2_rcg_set_rate_mnd,
+ .freq_tbl = ftbl_gcc_usb20_master_clk,
+ .current_freq = &rcg_dummy_freq,
+
+ .c = {
+ .dbg_name = "usb20_master_clk_src",
+ .ops = &clk_ops_rcg,
+ },
+};
+
static struct branch_clk gcc_usb30_master_clk = {
.cbcr_reg = (uint32_t *) USB30_MASTER_CBCR,
.bcr_reg = (uint32_t *) USB_30_BCR,
@@ -370,6 +405,17 @@
},
};
+static struct branch_clk gcc_usb20_master_clk = {
+ .cbcr_reg = (uint32_t *) USB20_MASTER_CBCR,
+ .bcr_reg = (uint32_t *) USB_20_BCR,
+ .parent = &usb20_master_clk_src.c,
+
+ .c = {
+ .dbg_name = "usb20_master_clk",
+ .ops = &clk_ops_branch,
+ },
+};
+
static struct branch_clk gcc_aggre2_usb3_axi_clk = {
.cbcr_reg = (uint32_t *) GCC_AGGRE2_USB3_AXI_CBCR,
.parent = &usb30_master_clk_src.c,
@@ -385,6 +431,11 @@
F_END
};
+static struct clk_freq_tbl ftbl_gcc_usb20_mock_utmi_clk_src[] = {
+ F( 60000000, gpll0, 10, 0, 0),
+ F_END
+};
+
static struct rcg_clk usb30_mock_utmi_clk_src = {
.cmd_reg = (uint32_t *) USB30_MOCK_UTMI_CMD_RCGR,
.cfg_reg = (uint32_t *) USB30_MOCK_UTMI_CFG_RCGR,
@@ -398,6 +449,19 @@
},
};
+static struct rcg_clk usb20_mock_utmi_clk_src = {
+ .cmd_reg = (uint32_t *) USB20_MOCK_UTMI_CMD_RCGR,
+ .cfg_reg = (uint32_t *) USB20_MOCK_UTMI_CFG_RCGR,
+ .set_rate = clock_lib2_rcg_set_rate_hid,
+ .freq_tbl = ftbl_gcc_usb20_mock_utmi_clk_src,
+ .current_freq = &rcg_dummy_freq,
+
+ .c = {
+ .dbg_name = "usb20_mock_utmi_clk_src",
+ .ops = &clk_ops_rcg,
+ },
+};
+
static struct branch_clk gcc_usb30_mock_utmi_clk = {
.cbcr_reg = (uint32_t *) USB30_MOCK_UTMI_CBCR,
.has_sibling = 0,
@@ -409,6 +473,18 @@
},
};
+static struct branch_clk gcc_usb20_mock_utmi_clk = {
+ .cbcr_reg = (uint32_t *) USB20_MOCK_UTMI_CBCR,
+ .has_sibling = 0,
+ .parent = &usb20_mock_utmi_clk_src.c,
+
+ .c = {
+ .dbg_name = "usb20_mock_utmi_clk",
+ .ops = &clk_ops_branch,
+ },
+};
+
+
static struct branch_clk gcc_usb30_sleep_clk = {
.cbcr_reg = (uint32_t *) USB30_SLEEP_CBCR,
.has_sibling = 1,
@@ -419,6 +495,16 @@
},
};
+static struct branch_clk gcc_usb20_sleep_clk = {
+ .cbcr_reg = (uint32_t *) USB20_SLEEP_CBCR,
+ .has_sibling = 1,
+
+ .c = {
+ .dbg_name = "usb20_sleep_clk",
+ .ops = &clk_ops_branch,
+ },
+};
+
static struct clk_freq_tbl ftbl_gcc_usb30_phy_aux_clk_src[] = {
F( 1200000, cxo, 16, 0, 0),
F_END
@@ -728,6 +814,77 @@
},
};
+static struct branch_clk mdss_hdmi_ahb_clk = {
+ .cbcr_reg = (uint32_t *) MDSS_HDMI_AHB_CBCR,
+ .has_sibling = 1,
+ .c = {
+ .dbg_name = "mdss_hdmi_ahb_clk",
+ .ops = &clk_ops_branch,
+ },
+};
+
+static struct clk_freq_tbl ftbl_mdss_hdmi_clk[] = {
+ F_MM( 19200000, cxo, 1, 0, 0),
+ F_END
+};
+
+static struct rcg_clk hdmi_clk_src = {
+ .cmd_reg = (uint32_t *) HDMI_CMD_RCGR,
+ .cfg_reg = (uint32_t *) HDMI_CFG_RCGR,
+ .set_rate = clock_lib2_rcg_set_rate_hid,
+ .freq_tbl = ftbl_mdss_hdmi_clk,
+ .current_freq = &rcg_dummy_freq,
+ .c = {
+ .dbg_name = "hdmi_clk_src",
+ .ops = &clk_ops_rcg,
+ },
+};
+
+static struct branch_clk mdss_hdmi_clk = {
+ .cbcr_reg = (uint32_t *) MDSS_HDMI_CBCR,
+ .has_sibling = 0,
+ .parent = &hdmi_clk_src.c,
+ .c = {
+ .dbg_name = "mdss_hdmi_clk",
+ .ops = &clk_ops_branch,
+ },
+};
+
+static struct clk_freq_tbl ftbl_mdss_extpclk_clk[] = {
+ F_MDSS( 74250000, hdmipll, 1, 0, 0),
+ F_MDSS( 25200000, hdmipll, 1, 0, 0),
+ F_MDSS( 27000000, hdmipll, 1, 0, 0),
+ F_MDSS( 27030000, hdmipll, 1, 0, 0),
+ F_MDSS( 27070000, hdmipll, 1, 0, 0),
+ F_MDSS( 65000000, hdmipll, 1, 0, 0),
+ F_MDSS(108000000, hdmipll, 1, 0, 0),
+ F_MDSS(148500000, hdmipll, 1, 0, 0),
+ F_MDSS(268500000, hdmipll, 1, 0, 0),
+ F_MDSS(297000000, hdmipll, 1, 0, 0),
+ F_END
+};
+
+static struct rcg_clk extpclk_clk_src = {
+ .cmd_reg = (uint32_t *) EXTPCLK_CMD_RCGR,
+ .cfg_reg = (uint32_t *) EXTPCLK_CFG_RCGR,
+ .set_rate = clock_lib2_rcg_set_rate_hid,
+ .freq_tbl = ftbl_mdss_extpclk_clk,
+ .current_freq = &rcg_dummy_freq,
+ .c = {
+ .dbg_name = "extpclk_clk_src",
+ .ops = &clk_ops_rcg,
+ },
+};
+
+static struct branch_clk mdss_extpclk_clk = {
+ .cbcr_reg = (uint32_t *) MDSS_EXTPCLK_CBCR,
+ .has_sibling = 0,
+ .parent = &extpclk_clk_src.c,
+ .c = {
+ .dbg_name = "mdss_extpclk_clk",
+ .ops = &clk_ops_branch,
+ },
+};
/* Clock lookup table */
static struct clk_lookup msm_msm8996_clocks[] =
@@ -750,6 +907,12 @@
CLK_LOOKUP("usb_phy_cfg_ahb2phy_clk", gcc_usb_phy_cfg_ahb2phy_clk.c),
+ /* USB20 clocks */
+ CLK_LOOKUP("usb20_noc_usb20_clk", gcc_periph_noc_usb20_ahb_clk.c),
+ CLK_LOOKUP("usb20_master_clk", gcc_usb20_master_clk.c),
+ CLK_LOOKUP("usb20_mock_utmi_clk", gcc_usb20_mock_utmi_clk.c),
+ CLK_LOOKUP("usb20_sleep_clk", gcc_usb20_sleep_clk.c),
+
/* mdss clocks */
CLK_LOOKUP("mdss_mdp_clk", mdss_mdp_clk.c),
CLK_LOOKUP("mdss_vsync_clk", mdss_vsync_clk.c),
@@ -772,6 +935,11 @@
gcc_blsp2_qup2_i2c_apps_clk_src.c),
CLK_LOOKUP("gcc_blsp2_qup2_i2c_apps_clk",
gcc_blsp2_qup2_i2c_apps_clk.c),
+
+ /* HDMI clocks*/
+ CLK_LOOKUP("hdmi_ahb_clk", mdss_hdmi_ahb_clk.c),
+ CLK_LOOKUP("hdmi_core_clk", mdss_hdmi_clk.c),
+ CLK_LOOKUP("hdmi_extp_clk", mdss_extpclk_clk.c),
};
void platform_clock_init(void)
diff --git a/platform/msm8996/platform.c b/platform/msm8996/platform.c
index 79bf7c9..a3c2d3e 100644
--- a/platform/msm8996/platform.c
+++ b/platform/msm8996/platform.c
@@ -181,3 +181,46 @@
return false;
}
+
+
+/* USB platform specific bases*/
+uint32_t usb_ctrl_base()
+{
+ if (board_hardware_id() == HW_PLATFORM_SBC)
+ return MSM_USB20_SEC_BASE;
+ else
+ return MSM_USB30_PRIM_BASE;
+
+}
+
+uint32_t usb_qscratch_base()
+{
+ if (board_hardware_id() == HW_PLATFORM_SBC)
+ return MSM_USB20_SEC_QSCRATCH_BASE;
+ else
+ return MSM_USB30_QSCRATCH_PRIM_BASE;
+}
+
+uint32_t usb_phy_base()
+{
+ if (board_hardware_id() == HW_PLATFORM_SBC)
+ return QUSB2_SEC_PHY_BASE;
+ else
+ return QUSB2_PRIM_PHY_BASE;
+}
+
+uint32_t usb_phy_bcr()
+{
+ if (board_hardware_id() == HW_PLATFORM_SBC)
+ return GCC_QUSB2_SEC_PHY_BCR;
+ else
+ return GCC_QUSB2_PRIM_PHY_BCR;
+}
+
+int usb_irq()
+{
+ if (board_hardware_id() == HW_PLATFORM_SBC)
+ return USB20_IRQ;
+ else
+ return USB30_IRQ;
+}
diff --git a/platform/msm_shared/board.c b/platform/msm_shared/board.c
index 19ec937..a4d3be4 100644
--- a/platform/msm_shared/board.c
+++ b/platform/msm_shared/board.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2012-2015, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2012-2016, The Linux Foundation. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
@@ -289,30 +289,26 @@
void pmic_info_populate()
{
- struct smem_board_info_v11 *bi_v11=NULL;
- unsigned int board_info_len = 0;
- unsigned ret = 0;
uint32_t pmic_type = 0;
+ void *smem_board_info_addr = NULL;
+ uint32_t smem_board_info_size = 0;
if (format_minor < 0xB)
{
// not needed for smem versions < 0xB
return;
}
-
- board_info_len = sizeof(struct smem_board_info_v11) + board.num_pmics * sizeof(struct smem_pmic_info);
- if(!(bi_v11 = malloc(board_info_len)))
+ smem_board_info_addr = smem_get_alloc_entry(SMEM_BOARD_INFO_LOCATION, &smem_board_info_size);
+ if (smem_board_info_addr == NULL)
{
- dprintf(CRITICAL, "Error allocating memory for board structure\n");
+ dprintf(CRITICAL, "Error reading the smem board info address\n");
ASSERT(0);
}
- ret = smem_read_alloc_entry(SMEM_BOARD_INFO_LOCATION,
- bi_v11,
- board_info_len);
- if (ret)
+
+ if (smem_board_info_size < board.pmic_array_offset)
{
- dprintf(CRITICAL, "Error reading from SMEM for populating pmic info\n");
- goto free_bi_v11;
+ dprintf(CRITICAL, "Invalid SMEM board info\n");
+ ASSERT(0);
}
if(!(board.pmic_info_array = malloc(board.num_pmics * sizeof(struct board_pmic_data))))
@@ -320,10 +316,11 @@
dprintf(CRITICAL, "Error allocating memory for pmic info array\n");
ASSERT(0);
}
+
struct board_pmic_data *info = board.pmic_info_array;
for (uint8_t i = 0; i < board.num_pmics; i++)
{
- memcpy(info, (void *)(bi_v11) + board.pmic_array_offset + (i * sizeof(struct smem_pmic_info)), sizeof(struct smem_pmic_info));
+ memcpy(info, smem_board_info_addr + board.pmic_array_offset + (i * sizeof(struct smem_pmic_info)), sizeof(struct smem_pmic_info));
/*
* fill in pimc_board_info with pmic type and pmic version information
* bit no |31 24|23 16|15 8|7 0|
@@ -335,8 +332,6 @@
((info->pmic_version & 0xff) << 8) | (pmic_type & 0xff);
info++;
}
-free_bi_v11:
- free(bi_v11);
}
void board_init()
diff --git a/platform/msm_shared/hsusb.c b/platform/msm_shared/hsusb.c
index 5f8d3e4..9ebe36e 100644
--- a/platform/msm_shared/hsusb.c
+++ b/platform/msm_shared/hsusb.c
@@ -2,7 +2,7 @@
* Copyright (c) 2008, Google Inc.
* All rights reserved.
*
- * Copyright (c) 2009-2015, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2009-2016, The Linux Foundation. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
@@ -62,7 +62,10 @@
{
struct udc_descriptor *desc;
if ((len > 255) || (len < 2) || (num > 255) || (type > 255))
- return 0;
+ {
+ dprintf(CRITICAL, "Invalid parameters for descriptor allocation\n");
+ ASSERT(0);
+ }
desc = malloc(sizeof(struct udc_descriptor) + len);
ASSERT(desc);
diff --git a/platform/msm_shared/include/mdp5.h b/platform/msm_shared/include/mdp5.h
index 2a72772..935e7a6 100644
--- a/platform/msm_shared/include/mdp5.h
+++ b/platform/msm_shared/include/mdp5.h
@@ -235,6 +235,15 @@
#define MDP_REG_PP_1_AUTOREFRESH_CONFIG REG_MDP(0x71830)
#define MDP_REG_PP_SLAVE_AUTOREFRESH_CONFIG REG_MDP(0x73030)
+/* Registers for programming the CDM hardware in bypass mode. */
+#define CDM_HDMI_PACK_OP_MODE REG_MDP(0x7A400)
+#define MDP_OUT_CTL_0 REG_MDP(0x01410)
+#define MDP_INTF_3_INTF_CONFIG REG_MDP(0x6C804)
+#define CDM_CDWN2_OUT_SIZE REG_MDP(0x7A330)
+#define CDM_CDWN2_OP_MODE REG_MDP(0x7A300)
+#define CDM_CDWN2_CLAMP_OUT REG_MDP(0x7A304)
+#define CDM_CSC_10_OP_MODE REG_MDP(0x7A200)
+
void mdp_set_revision(int rev);
int mdp_get_revision();
int mdp_dsi_video_config(struct msm_panel_info *pinfo, struct fbcon_config *fb);
@@ -256,9 +265,11 @@
int target_edp_panel_disable(void);
int target_edp_bl_ctrl(int enable);
int mdss_hdmi_init(void);
+void mdss_hdmi_display_init(uint32_t rev, void *base);
int mdss_hdmi_on(struct msm_panel_info *pinfo);
int mdss_hdmi_config(struct msm_panel_info *pinfo, struct fbcon_config *fb);
void mdss_hdmi_get_vic(char *buf);
+void hdmi_phy_init(void);
int msm_display_off();
void display_shutdown(void);
diff --git a/platform/msm_shared/mdss_hdmi.c b/platform/msm_shared/mdss_hdmi.c
index 0741308..4908c19 100644
--- a/platform/msm_shared/mdss_hdmi.c
+++ b/platform/msm_shared/mdss_hdmi.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2010-2015, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2010-2016, The Linux Foundation. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
@@ -101,6 +101,8 @@
{10240, 247500}, {18816, 247500}, {20480, 247500} }),
};
+extern int msm_display_init(struct msm_fb_panel_data *pdata);
+
/* AVI INFOFRAME DATA */
#define NUM_MODES_AVI 20
#define AVI_MAX_DATA_BYTES 13
diff --git a/platform/msm_shared/qpic_nand.c b/platform/msm_shared/qpic_nand.c
index baba30d..3fec647 100644
--- a/platform/msm_shared/qpic_nand.c
+++ b/platform/msm_shared/qpic_nand.c
@@ -1378,6 +1378,12 @@
}
unsigned
+flash_num_pages_per_blk(void)
+{
+ return flash.num_pages_per_blk;
+}
+
+unsigned
flash_spare_size(void)
{
return flash.spare_size;
diff --git a/platform/msm_shared/rules.mk b/platform/msm_shared/rules.mk
index f426e93..be1a5f1 100755
--- a/platform/msm_shared/rules.mk
+++ b/platform/msm_shared/rules.mk
@@ -582,7 +582,8 @@
$(LOCAL_DIR)/mipi_dsi_autopll_thulium.o \
$(LOCAL_DIR)/shutdown_detect.o \
$(LOCAL_DIR)/i2c_qup.o \
- $(LOCAL_DIR)/mipi_dsi_i2c.o
+ $(LOCAL_DIR)/mipi_dsi_i2c.o \
+ $(LOCAL_DIR)/mdss_hdmi.o
endif
ifeq ($(ENABLE_UFS_SUPPORT), 1)
diff --git a/platform/msm_shared/usb30_udc.c b/platform/msm_shared/usb30_udc.c
index f175cb8..a2923f1 100644
--- a/platform/msm_shared/usb30_udc.c
+++ b/platform/msm_shared/usb30_udc.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2013-2015, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2013-2016, The Linux Foundation. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
@@ -1380,7 +1380,10 @@
{
struct udc_descriptor *desc;
if ((len > 255) || (len < 2) || (num > 255) || (type > 255))
- return 0;
+ {
+ dprintf(CRITICAL, "Invalid parameters for descriptor allocation\n");
+ ASSERT(0);
+ }
desc = malloc(sizeof(struct udc_descriptor) + len);
ASSERT(desc);
diff --git a/target/msm8996/include/target/display.h b/target/msm8996/include/target/display.h
index 5b21a1f..9ee5ec3 100644
--- a/target/msm8996/include/target/display.h
+++ b/target/msm8996/include/target/display.h
@@ -1,4 +1,4 @@
-/* Copyright (c) 2015, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2015-2016, The Linux Foundation. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
@@ -33,6 +33,7 @@
/* HEADER files */
/*---------------------------------------------------------------------------*/
#include <display_resource.h>
+#include <msm_panel.h>
/*---------------------------------------------------------------------------*/
/* Target Physical configuration */
@@ -67,6 +68,7 @@
#define DISPLAY_CMDLINE_PREFIX " mdss_mdp.panel="
#define MIPI_FB_ADDR 0x83400000
+#define HDMI_FB_ADDR 0xB1C00000
#define MIPI_HSYNC_PULSE_WIDTH 16
#define MIPI_HSYNC_BACK_PORCH_DCLK 32
@@ -79,7 +81,8 @@
#define PWM_BL_LPG_CHAN_ID 4 /* lpg_out<3> */
#define HDMI_PANEL_NAME "hdmi"
-#define HDMI_CONTROLLER_STRING "hdmi:0"
+#define HDMI_CONTROLLER_STRING "hdmi:"
+#define HDMI_VIC_LEN 5
/*---------------------------------------------------------------------------*/
/* Functions */
@@ -93,5 +96,9 @@
void target_force_cont_splash_disable(uint8_t override);
uint8_t target_panel_auto_detect_enabled();
void target_set_switch_gpio(int enable_dsi2hdmibridge);
+int target_hdmi_pll_clock(uint8_t enable, struct msm_panel_info *pinfo);
+int target_hdmi_panel_clock(uint8_t enable, struct msm_panel_info *pinfo);
+int target_hdmi_regulator_ctrl(uint8_t enable);
+int target_hdmi_gpio_ctrl(uint8_t enable);
#endif
diff --git a/target/msm8996/init.c b/target/msm8996/init.c
index 25c1b14..51051c9 100644
--- a/target/msm8996/init.c
+++ b/target/msm8996/init.c
@@ -500,6 +500,11 @@
qusb2_phy_reset();
}
+void target_usb_phy_sec_reset()
+{
+ qusb2_phy_reset();
+}
+
target_usb_iface_t* target_usb30_init()
{
target_usb_iface_t *t_usb_iface;
@@ -507,9 +512,20 @@
t_usb_iface = calloc(1, sizeof(target_usb_iface_t));
ASSERT(t_usb_iface);
- t_usb_iface->phy_init = usb30_qmp_phy_init;
- t_usb_iface->phy_reset = target_usb_phy_reset;
- t_usb_iface->clock_init = clock_usb30_init;
+
+ /* for SBC we use secondary port */
+ if (board_hardware_id() == HW_PLATFORM_SBC)
+ {
+ /* secondary port have no QMP phy,use only QUSB2 phy that have only reset */
+ t_usb_iface->phy_init = NULL;
+ t_usb_iface->phy_reset = target_usb_phy_sec_reset;
+ t_usb_iface->clock_init = clock_usb20_init;
+ } else {
+ t_usb_iface->phy_init = usb30_qmp_phy_init;
+ t_usb_iface->phy_reset = target_usb_phy_reset;
+ t_usb_iface->clock_init = clock_usb30_init;
+ }
+
t_usb_iface->vbus_override = 1;
return t_usb_iface;
diff --git a/target/msm8996/regulator.c b/target/msm8996/regulator.c
index 909082d..a95a42f 100644
--- a/target/msm8996/regulator.c
+++ b/target/msm8996/regulator.c
@@ -1,4 +1,4 @@
-/* Copyright (c) 2014-2015, The Linux Foundation. All rights reserved.
+/* Copyright (c) 2014-2016, The Linux Foundation. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
@@ -48,6 +48,23 @@
},
};
+static uint32_t ldo12[][11]=
+{
+ {
+ LDOA_RES_TYPE, 12,
+ KEY_SOFTWARE_ENABLE, 4, GENERIC_DISABLE,
+ KEY_MICRO_VOLT, 4, 0,
+ KEY_CURRENT, 4, 0,
+ },
+
+ {
+ LDOA_RES_TYPE, 12,
+ KEY_SOFTWARE_ENABLE, 4, GENERIC_ENABLE,
+ KEY_MICRO_VOLT, 4, 1800000,
+ KEY_CURRENT, 4, 11,
+ },
+};
+
static uint32_t ldo14[][11]=
{
{
@@ -88,6 +105,9 @@
if (enable & REG_LDO2)
rpm_send_data(&ldo2[GENERIC_ENABLE][0], 36, RPM_REQUEST_TYPE);
+ if (enable & REG_LDO12)
+ rpm_send_data(&ldo12[GENERIC_ENABLE][0], 36, RPM_REQUEST_TYPE);
+
if (enable & REG_LDO14)
rpm_send_data(&ldo14[GENERIC_ENABLE][0], 36, RPM_REQUEST_TYPE);
@@ -100,6 +120,9 @@
if (enable & REG_LDO2)
rpm_send_data(&ldo2[GENERIC_DISABLE][0], 36, RPM_REQUEST_TYPE);
+ if (enable & REG_LDO12)
+ rpm_send_data(&ldo12[GENERIC_DISABLE][0], 36, RPM_REQUEST_TYPE);
+
if (enable & REG_LDO14)
rpm_send_data(&ldo14[GENERIC_DISABLE][0], 36, RPM_REQUEST_TYPE);
diff --git a/target/msm8996/rules.mk b/target/msm8996/rules.mk
index e59bfc2..c6918f7 100644
--- a/target/msm8996/rules.mk
+++ b/target/msm8996/rules.mk
@@ -8,13 +8,13 @@
PLATFORM := msm8996
-MEMBASE := 0x91600000 # SDRAM
+MEMBASE := 0x91800000 # SDRAM
MEMSIZE := 0x00400000 # 4MB
BASE_ADDR := 0x0000000
-SCRATCH_ADDR := 0x91C00000
-SCRATCH_SIZE := 740
+SCRATCH_ADDR := 0x91E00000
+SCRATCH_SIZE := 738
KERNEL_ADDR := 0x80000000
KERNEL_SIZE := 88
diff --git a/target/msm8996/target_display.c b/target/msm8996/target_display.c
index 5086451..3709094 100644
--- a/target/msm8996/target_display.c
+++ b/target/msm8996/target_display.c
@@ -92,6 +92,88 @@
"msmgpio", 105, 3, 1, 0, 1
};
+/* gpio name, id, strength, direction, pull, state. */
+static struct gpio_pin hdmi_cec_gpio = { /* CEC */
+ "msmgpio", 31, 0, 2, 3, 1
+};
+
+static struct gpio_pin hdmi_ddc_clk_gpio = { /* DDC CLK */
+ "msmgpio", 32, 0, 2, 3, 1
+};
+
+static struct gpio_pin hdmi_ddc_data_gpio = { /* DDC DATA */
+ "msmgpio", 33, 0, 2, 3, 1
+};
+
+static struct gpio_pin hdmi_hpd_gpio = { /* HPD, input */
+ "msmgpio", 34, 7, 0, 1, 1
+};
+
+static void target_hdmi_ldo_enable(uint8_t enable)
+{
+ if (enable)
+ regulator_enable(REG_LDO12);
+ else
+ regulator_disable(REG_LDO12);
+}
+
+static void target_hdmi_mpp4_enable(uint8_t enable)
+{
+ struct pm8x41_mpp mpp;
+
+ /* Enable MPP4 */
+ pmi8994_config_mpp_slave_id(0);
+
+ mpp.base = PM8x41_MMP4_BASE;
+ mpp.vin = MPP_VIN2;
+ mpp.mode = MPP_HIGH;;
+ if (enable) {
+ pm8x41_config_output_mpp(&mpp);
+ pm8x41_enable_mpp(&mpp, MPP_ENABLE);
+ } else {
+ pm8x41_enable_mpp(&mpp, MPP_DISABLE);
+ }
+
+ /* Need delay before power on regulators */
+ mdelay(20);
+}
+
+int target_hdmi_regulator_ctrl(uint8_t enable)
+{
+ target_hdmi_ldo_enable(enable);
+
+ target_hdmi_mpp4_enable(enable);
+
+ return 0;
+}
+
+int target_hdmi_gpio_ctrl(uint8_t enable)
+{
+ gpio_tlmm_config(hdmi_cec_gpio.pin_id, 1, /* gpio 31, CEC */
+ hdmi_cec_gpio.pin_direction, hdmi_cec_gpio.pin_pull,
+ hdmi_cec_gpio.pin_strength, hdmi_cec_gpio.pin_state);
+
+ gpio_tlmm_config(hdmi_ddc_clk_gpio.pin_id, 1, /* gpio 32, DDC CLK */
+ hdmi_ddc_clk_gpio.pin_direction, hdmi_ddc_clk_gpio.pin_pull,
+ hdmi_ddc_clk_gpio.pin_strength, hdmi_ddc_clk_gpio.pin_state);
+
+
+ gpio_tlmm_config(hdmi_ddc_data_gpio.pin_id, 1, /* gpio 33, DDC DATA */
+ hdmi_ddc_data_gpio.pin_direction, hdmi_ddc_data_gpio.pin_pull,
+ hdmi_ddc_data_gpio.pin_strength, hdmi_ddc_data_gpio.pin_state);
+
+ gpio_tlmm_config(hdmi_hpd_gpio.pin_id, 1, /* gpio 34, HPD */
+ hdmi_hpd_gpio.pin_direction, hdmi_hpd_gpio.pin_pull,
+ hdmi_hpd_gpio.pin_strength, hdmi_hpd_gpio.pin_state);
+
+ gpio_set(hdmi_cec_gpio.pin_id, hdmi_cec_gpio.pin_direction);
+ gpio_set(hdmi_ddc_clk_gpio.pin_id, hdmi_ddc_clk_gpio.pin_direction);
+ gpio_set(hdmi_ddc_data_gpio.pin_id, hdmi_ddc_data_gpio.pin_direction);
+ gpio_set(hdmi_hpd_gpio.pin_id, hdmi_hpd_gpio.pin_direction);
+
+ return NO_ERROR;
+}
+
static uint32_t thulium_dsi_pll_lock_status(uint32_t pll_base, uint32_t off,
uint32_t bit)
{
@@ -579,6 +661,7 @@
int prefix_string_len = strlen(DISPLAY_CMDLINE_PREFIX);
bool ret = true;
struct oem_panel_data oem = mdss_dsi_get_oem_data();
+ char vic_buf[HDMI_VIC_LEN] = "0";
if (!strcmp(oem.panel, HDMI_PANEL_NAME)) {
if (buf_size < (prefix_string_len + LK_OVERRIDE_PANEL_LEN +
@@ -592,6 +675,9 @@
strlcat(pbuf, LK_OVERRIDE_PANEL, buf_size);
buf_size -= LK_OVERRIDE_PANEL_LEN;
strlcat(pbuf, HDMI_CONTROLLER_STRING, buf_size);
+ buf_size -= strlen(HDMI_CONTROLLER_STRING);
+ mdss_hdmi_get_vic(vic_buf);
+ strlcat(pbuf, vic_buf, buf_size);
} else {
ret = gcdb_display_cmdline_arg(pbuf, buf_size);
}
@@ -629,6 +715,8 @@
oem.panel);
return;
} else if (!strcmp(oem.panel, HDMI_PANEL_NAME)) {
+ dprintf(INFO, "%s: HDMI is primary\n", __func__);
+ mdss_hdmi_display_init(MDP_REV_50, (void *) HDMI_FB_ADDR);
return;
}